GnuCOBOL:尝试创建递归用户定义函数

GnuCOBOL: Trying to create a recursive user defined function

我正在尝试使用 GnuCOBOL 2.0.0 创建一个递归的用户定义函数,但是当我尝试 运行 调用程序时它崩溃并出现“分段失败”错误。

这是函数:

identification division.
function-id.   FATORIAL.
author.        Paulo Andre Dias.
date-written.  15/02/2017.
remarks.       Calcula o fatorial do numero N informado via argumento.     

environment division.
configuration section.

data division.
working-storage section.
77 ws-fatorial-n-menos-1    pic 9(006) value zeros.

linkage section.
01 lk-n                     pic 9(006).
01 lk-fatorial              pic 9(006). 

procedure division using lk-n returning lk-fatorial.
principal.

    if lk-n = zeros
        move 1 to lk-fatorial
    else
        move FATORIAL(lk-n - 1) to ws-fatorial-n-menos-1
        compute lk-fatorial = lk-n * ws-fatorial-n-menos-1
    end-if

    goback.

end function FATORIAL.

这是调用程序:

identification division.
program-id. gtc002.

environment division.
configuration section.
repository.
    function FATORIAL.

data division.
working-storage section.
77 ws-n pic 9(006) value zeros.

procedure division.
main.
    display "Entre com um numero inteiro positivo (ou zero para encerrar):"
    accept ws-n from console
    if ws-n = zeros
        stop run
    else
        display "O fatorial de " ws-n " e' " FATORIAL(ws-n)
    end-if
    go to main.

事情是这样的:

[aeisxpad ~/cbl]$ ../bin/gtc002
Entre com um numero inteiro positivo (ou zero para encerrar)::
5
Falha de segmentação
[aeisxpad ~/cbl]$ 

我错过了什么吗?有什么想法吗?

提前谢谢大家。

用户定义函数和 GnuCOBOL 错误的解决方法。

就 BINARY 和 DISPLAY 用法而言,用户定义的 FUNCTION 调用未正确编组。值作为用法显示传递给图片 9。尝试将 ws-n 更改为 USAGE BINARY。这将在调用中强制使用本机数字,(然后需要在 FATORIAL 本身的 lk-n 的链接部分中匹配。

   identification division.
   program-id. gtc002.

   environment division.
   configuration section.
   repository.
       function FATORIAL.

   data division.
   working-storage section.
  *> 77 ws-n pic 9(006) value zeros.
   77 ws-n usage binary-long.

   procedure division.
   main.
       display "Entre com um numero inteiro positivo" &
               " (ou zero para encerrar):"
       accept ws-n from console
       if ws-n = zeros
           stop run
       else
           display "O fatorial de " ws-n " e' " FATORIAL(ws-n)
       end-if
       go to main.

   identification division.
   function-id.   FATORIAL.
   author.        Paulo Andre Dias.
   date-written.  15/02/2017.
   remarks. Calcula o fatorial do numero N informado via argumento.     
   
   environment division.
   configuration section.

   data division.
   working-storage section.
   77 ws-fatorial-n-menos-1    pic 9(006) value zeros.

   linkage section.
  *> 01 lk-n                     pic 9(006).
   01 lk-n                     usage binary-long.
   01 lk-fatorial              pic 9(006).

   procedure division using lk-n returning lk-fatorial.
   principal.

       if lk-n = zeros
           move 1 to lk-fatorial
       else
           move FATORIAL(lk-n - 1) to ws-fatorial-n-menos-1
           compute lk-fatorial = lk-n * ws-fatorial-n-menos-1
       end-if

       goback.

   end function FATORIAL.

在这里给予,

prompt$ cobc -g -xj gtc002.cob FACTORIAL.cob
Entre com um numero inteiro positivo (ou zero para encerrar):
3
O fatorial de +0000000003 e' 000006
Entre com um numero inteiro positivo (ou zero para encerrar):
5
O fatorial de +0000000005 e' 000120
Entre com um numero inteiro positivo (ou zero para encerrar):
7
O fatorial de +0000000007 e' 005040
Entre com um numero inteiro positivo (ou zero para encerrar):
0

请原谅稍微重新格式化,上面的版本应该作为 FIXED 或 FREE 格式 COBOL 编译

原版将 ASCII“00005”传递给函数,尝试在不正确封送为 USAGE BINARY 时递归大量次数(这是 GnuCOBOL 中的错误)。正如@Simon Sobisch 指出的那样,这将在某一天得到解决,但目前一个合理的解决方法是使用数字的实际 USAGE BINARY 参数而不是 PIC 9 COBOL 字段对用户定义的函数进行编码。

该解决方法适用于递归或非递归函数。

With literals in source, use FUNCTION NUMVAL(123) for 123. GnuCOBOL cobc中源文本文字默认为"123" PIC 9 (usage DISPLAY)形式,调用时需要强制使用USAGE BINARY numeric当前版本中的用户定义函数。