如何在没有大量代码的情况下处理这个数组?

时间:2020-11-30 09:22:24

I'll start by admitting this is for my homework and I don't expect anything specific just a tip perhaps. The input file is just one 30 byte field that contains names. The output file is two fields 30 bytes each. I'll list the code to show what I mean by this. The program needs to read the input file putting the names into an array and then print them to the two fields in the output file. It would be simple enough if the out put file was like this:

首先我得承认这是我的作业,我不期望有什么特别的东西,也许只是一个提示。输入文件只是一个包含名称的30字节字段。输出文件是两个字段,每个字段30字节。我将列出代码来说明我的意思。程序需要读取将名称放入数组的输入文件,然后将它们打印到输出文件中的两个字段。如果out put文件是这样的话就足够简单了:

name 1             name 2
name 3             name 4
etc...

but it's supposed to be:

但它应该是:

name 1             name 55
name 2             name 56
....
name 54            name 108

I'm not quite understanding how I can code the program to do this without having 54 lines of code (1 for each line in the output). Well here's the code I have so far:

我不太理解如何在没有54行代码(输出中的每一行都有1行代码)的情况下对程序进行编码。这是我到目前为止的代码:

ENVIRONMENT DIVISION.                                        
INPUT-OUTPUT SECTION.                                        
FILE-CONTROL.                                                

SELECT NAMELIST-FILE-IN                                  
    ASSIGN TO 'NAMELIST.SEQ'                             
    ORGANIZATION IS LINE SEQUENTIAL.                     

SELECT NAMELIST-FILE-OUT                                 
    ASSIGN TO 'NAMELIST.RPT'                             
    ORGANIZATION IS LINE SEQUENTIAL.                     

 DATA DIVISION.                                               
 FILE SECTION.                                                

 FD NAMELIST-FILE-IN.                                         
    01 NAME-IN                       PIC X(30).                  

 FD NAMELIST-FILE-OUT.                                        
    01 NAME-OUT                      PIC X(60).                  

WORKING-STORAGE SECTION.                                     
    01 ARE-THERE-MORE-RECORDS        PIC X(3)  VALUE 'YES'.      
    01 PAGE-CTR                      PIC 99    VALUE ZERO.       
    01 SUB                           PIC 999   VALUE 1.          
    01 LEFT-NAME                     PIC 99    VALUE 54.         
    01 RIGHT-NAME                    PIC 9(3)  VALUE 108.        

01 WS-DATE.                                                  
    05 RUN-YEAR                  PIC XX.                     
    05 RUN-MONTH                 PIC XX.                     
    05 RUN-DAY                   PIC XX.                     

01 HEADING-LINE.                                             
    05                           PIC X(15) VALUE SPACES.     
    05                           PIC X(20)                   
        VALUE 'NAME LIST REPORT'.                            
    05 HL-DATE.                                              
        10  DAY-HL               PIC XX.                     
        10                       PIC X     VALUE '/'.        
        10  MONTH-HL             PIC XX.                     
        10                       PIC X     VALUE '/'.        
        10  YEAR-HL              PIC XX.                     
    05                           PIC X(3)  VALUE SPACES.     
    05                           PIC X(5)  VALUE 'PAGE'.     
    05  PAGE-NUMBER-HL           PIC Z9    VALUE 1.          

01 DETAIL-LINE.                                              
    05 NAME-LEFT                 PIC X(30).                  
    05 NAME-RIGHT                PIC X(30).                  

01 NAME-ARRAY.                                               
    05 NAME-X   OCCURS 108       PIC X(30).                  

PROCEDURE DIVISION.                                          
100-MAIN.                                                    
    OPEN INPUT NAMELIST-FILE-IN                              
    OPEN OUTPUT NAMELIST-FILE-OUT                            

    ACCEPT WS-DATE FROM DATE.                                
        MOVE RUN-MONTH TO MONTH-HL                           
        MOVE RUN-DAY TO DAY-HL                               
        MOVE RUN-YEAR TO YEAR-HL                             

    PERFORM 200-ACCEPT-INPUT                                 


    CLOSE NAMELIST-FILE-IN                                   
    CLOSE NAMELIST-FILE-OUT                                  
    STOP RUN.                                                

200-ACCEPT-INPUT.                                            
    PERFORM UNTIL SUB > 108                                  
        READ NAMELIST-FILE-IN                                
        MOVE NAME-IN TO NAME-X (SUB)                         
        ADD 1 TO SUB                                         
    END-PERFORM                                              

    PERFORM 300-PRINT-ONE-PAGE.                              

300-PRINT-ONE-PAGE.                                          
    WRITE NAME-OUT FROM HEADING-LINE                         
        AFTER ADVANCING PAGE                                 
    ADD 1 TO PAGE-CTR                                        

Here's the final code for this program if anyone is interested in seeing it.

如果有人有兴趣的话,这是这个程序的最终代码。

ENVIRONMENT DIVISION.                                            
INPUT-OUTPUT SECTION.                                            
FILE-CONTROL.                                                    

    SELECT NAMELIST-FILE-IN                                      
        ASSIGN TO 'NAMELIST.SEQ'                                 
        ORGANIZATION IS LINE SEQUENTIAL.                         

    SELECT NAMELIST-FILE-OUT                                     
        ASSIGN TO 'NAMELIST.RPT'                                 
        ORGANIZATION IS LINE SEQUENTIAL.                         

DATA DIVISION.                                                   
FILE SECTION.                                                    

FD NAMELIST-FILE-IN.                                             
01 NAME-IN                       PIC X(30).                      

FD NAMELIST-FILE-OUT.                                            
01 NAME-OUT                      PIC X(80).                      

WORKING-STORAGE SECTION.                                         
01 ARE-THERE-MORE-RECORDS        PIC X(3)  VALUE 'YES'.          
01 PAGE-CTR                      PIC 99    VALUE ZERO.           
01 SUB                           PIC 999.                        
01 SUB2                          PIC 999.                        
01 LEFT-NAME                     PIC 99    VALUE 54.             
01 RIGHT-NAME                    PIC 9(3)  VALUE 108.            

01 WS-DATE.                                                      
    05 RUN-YEAR                  PIC XX.                         
    05 RUN-MONTH                 PIC XX.                         
    05 RUN-DAY                   PIC XX.                         

01 HEADING-LINE.                                                 
    05                           PIC X(26) VALUE SPACES.         
    05                           PIC X(35)                       
        VALUE 'NAME LIST REPORT'.                                
    05 HL-DATE.                                                  
        10  DAY-HL               PIC XX.                         
        10                       PIC X     VALUE '/'.            
        10  MONTH-HL             PIC XX.                         
        10                       PIC X     VALUE '/'.            
        10  YEAR-HL              PIC XX.                         
    05                           PIC X(3)  VALUE SPACES.         
    05                           PIC X(5)  VALUE 'PAGE'.         
    05  PAGE-NUMBER-HL           PIC Z9.                         

01 DETAIL-LINE.                                                  
    05 NAME-LEFT                 PIC X(40).                      
    05 NAME-RIGHT                PIC X(40).                      

01 NAME-ARRAY.                                                   
    05 NAME-X   OCCURS 108       PIC X(30).                      

PROCEDURE DIVISION.                                              
100-MAIN.                                                        
    OPEN INPUT NAMELIST-FILE-IN                                  
    OPEN OUTPUT NAMELIST-FILE-OUT                                

    ACCEPT WS-DATE FROM DATE.                                    
        MOVE RUN-MONTH TO MONTH-HL                               
        MOVE RUN-DAY TO DAY-HL                                   
        MOVE RUN-YEAR TO YEAR-HL                                 

    PERFORM UNTIL ARE-THERE-MORE-RECORDS = 'NO'                  
        PERFORM 200-ACCEPT-INPUT                                 
    END-PERFORM                                                  

    CLOSE NAMELIST-FILE-IN                                       
    CLOSE NAMELIST-FILE-OUT                                      
    STOP RUN.                                                    

200-ACCEPT-INPUT.                                                
    INITIALIZE NAME-ARRAY                                        
    MOVE 1 TO SUB                                                

    PERFORM UNTIL SUB > 108 OR ARE-THERE-MORE-RECORDS = 'NO'     
        READ NAMELIST-FILE-IN                                    
            AT END                                               
                MOVE 'NO' TO ARE-THERE-MORE-RECORDS              
                MOVE SPACES TO NAME-IN                           
        END-READ                                                 
        MOVE NAME-IN TO NAME-X (SUB)                             
        ADD 1 TO SUB                                             

    END-PERFORM                                                  

    PERFORM 300-PRINT-ONE-PAGE.                                  

300-PRINT-ONE-PAGE.                                              
    ADD 1 TO PAGE-CTR                                            
    MOVE PAGE-CTR TO PAGE-NUMBER-HL                              
    WRITE NAME-OUT FROM HEADING-LINE                             
        AFTER ADVANCING PAGE                                     

    MOVE SPACES TO DETAIL-LINE                                   
    WRITE NAME-OUT FROM DETAIL-LINE                              
        AFTER ADVANCING 1                                        

    PERFORM VARYING SUB FROM 1 BY 1 UNTIL SUB > 54               
        MOVE NAME-X (SUB) TO NAME-LEFT                           
        COMPUTE SUB2 = SUB + 54                                  
        MOVE NAME-X (SUB2) TO NAME-RIGHT                         
        WRITE NAME-OUT FROM DETAIL-LINE                          
            AFTER ADVANCING 1                                    
    END-PERFORM.                                                 

2 个解决方案

#1


4  

I must apologize, I cannot think of a way to guide you without giving away the answer. I guess this is a spoiler alert.

我必须道歉,我想不出一种方法来引导你而不给出答案。我猜这是剧透警告。

One possible method you could use would be to add a variable SUB2 to Working-Storage and...

一种可能的方法是将变量SUB2添加到工作存储中,然后……

Perform Varying SUB From 1 By 1 Until SUB > 54
  Move NAME-X(SUB) to NAME-LEFT
  Compute SUB2 = SUB + 54
  MOVE NAME-X(SUB2) to NAME-RIGHT
  Write NAME-OUT from DETAIL-LINE After Advancing 1 Line
End-Perform

This is kind of kludgy and ties you to an array of 108 elements. You could use a record counter that you increment by 1 for each record read and then compute the values I show hardcoded in the sample above (54 is simply half of 108).

这是一种组装,将你连接到一个包含108个元素的数组。您可以使用一个记录计数器,对每次读取的记录增加1,然后计算我在上面的示例中显示的硬编码值(54只是108的一半)。

I don't show the page break logic, so perhaps I didn't give the whole show away.

我没有显示分页符的逻辑,所以可能我没有给出完整的显示。

I hope this helps you.

我希望这对你有帮助。

#2


1  

I would have 2 arrays.

有两个数组。

One containing the whole file.

一个包含整个文件的文件。

01 DETAIL-LINE-ARRAY.
    02 DETAIL-LINE OCCURS 54.                                              
        05 NAME-LEFT                 PIC X(30).                  
        05 NAME-RIGHT                PIC X(30).  

Another like you did with NAME-ARRAY

另一个就像你用名字数组做的那样。

Then I would populate first the DETAIL-LINE-ARRAY.

然后我将首先填充细节线数组。

I would read twice DETAIL-LINE-ARRAY to fill NAME-ARRAY

我将读取两次详细的线数组来填充名称数组

Then you can read sequentially NAME-ARRAY

然后可以读取顺序名称数组

==========================================================================

= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =

Another solution:

另一个解决方案:

You can read the file twice. While the first read, you take care only of the left name and populate NAME-ARRAY.

您可以读取该文件两次。在第一次读取时,只处理左名称并填充名称数组。

While the second reading, you take care only of the right name and continue to populate NAME-ARRAY.

在第二次读取时,只处理正确的名称并继续填充名称数组。

After the first and second read, you can read your array NAME-ARRAY.

在第一次和第二次读取之后,您可以读取数组名称数组。

==========================================================================

= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =

There is a problem with both last solutions : you have to know how much lines contains your file. Yep, you can have dynamic programming in cobol too :-)

最后两种解决方案都存在一个问题:您必须知道包含文件的行数。是的,您也可以用cobol进行动态编程:-)

You have to use SORT.

你必须使用排序。

In FILE SECTION add

在文件部分添加

SD  SORT-WORK
01  SORT-RECORD.
    05  SR-ORDER      PIC 9(09).
    05  SR-NAME       PIC X(30).

In your PROCEDURE DIVISION add (in pseude-code, you'll need to add some variables in your working storage section.

在过程分割中添加(在伪代码中,需要在工作存储部分中添加一些变量。

      SORT SORT-WORK
           ASCENDING SORT-ORDER
           INPUT PROCEDURE IS 1000-INPUT
           OUTPUT PROCEDURE IS 2000-OUTPUT

    1000-INPUT SECTION.
         MOVE 0 TO I.
         PERFORM until end-of-file of NAMELIST-FILE-IN  
           ADD 1 TO I
           READ left-name
           MOVE I TO SORT-ORDER
           MOVE left-name TO SR-NAME
    * This operation populates the sort file...
           RELEASE SORT-RECORD
         END-PERFORM.

         PERFORM until end-of-file of NAMELIST-FILE-IN
           ADD 1 TO I
           READ right-name
           MOVE I TO SORT-ORDER
           MOVE right-name TO SR-NAME
    * This operation populates the sort file...
           RELEASE SORT-RECORD     
         END-PERFORM.

         MOVE I TO WS-NB-NAMES.

     2000-OUTPUT SECTION.
         PERFORM VARYING I FROM 1 BY 1 UNTIL I > WS-NB-NAMES
* This operation returns the "next" record. It begins by the first, second...
           RETURN SORT-RECORD
           MOVE SR-NAME TO NAME-LEFT
           RETURN SORT-RECORD
           MOVE SR-NAME TO NAME-RIGHT
           WRITE NAMELIST-FILE-OUT FROM DETAIL-LINE
         END-PERFORM.

You have some example here for SORT

这里有一些排序的例子

Have fun !

玩得开心!

#1


4  

I must apologize, I cannot think of a way to guide you without giving away the answer. I guess this is a spoiler alert.

我必须道歉,我想不出一种方法来引导你而不给出答案。我猜这是剧透警告。

One possible method you could use would be to add a variable SUB2 to Working-Storage and...

一种可能的方法是将变量SUB2添加到工作存储中,然后……

Perform Varying SUB From 1 By 1 Until SUB > 54
  Move NAME-X(SUB) to NAME-LEFT
  Compute SUB2 = SUB + 54
  MOVE NAME-X(SUB2) to NAME-RIGHT
  Write NAME-OUT from DETAIL-LINE After Advancing 1 Line
End-Perform

This is kind of kludgy and ties you to an array of 108 elements. You could use a record counter that you increment by 1 for each record read and then compute the values I show hardcoded in the sample above (54 is simply half of 108).

这是一种组装,将你连接到一个包含108个元素的数组。您可以使用一个记录计数器,对每次读取的记录增加1,然后计算我在上面的示例中显示的硬编码值(54只是108的一半)。

I don't show the page break logic, so perhaps I didn't give the whole show away.

我没有显示分页符的逻辑,所以可能我没有给出完整的显示。

I hope this helps you.

我希望这对你有帮助。

#2


1  

I would have 2 arrays.

有两个数组。

One containing the whole file.

一个包含整个文件的文件。

01 DETAIL-LINE-ARRAY.
    02 DETAIL-LINE OCCURS 54.                                              
        05 NAME-LEFT                 PIC X(30).                  
        05 NAME-RIGHT                PIC X(30).  

Another like you did with NAME-ARRAY

另一个就像你用名字数组做的那样。

Then I would populate first the DETAIL-LINE-ARRAY.

然后我将首先填充细节线数组。

I would read twice DETAIL-LINE-ARRAY to fill NAME-ARRAY

我将读取两次详细的线数组来填充名称数组

Then you can read sequentially NAME-ARRAY

然后可以读取顺序名称数组

==========================================================================

= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =

Another solution:

另一个解决方案:

You can read the file twice. While the first read, you take care only of the left name and populate NAME-ARRAY.

您可以读取该文件两次。在第一次读取时,只处理左名称并填充名称数组。

While the second reading, you take care only of the right name and continue to populate NAME-ARRAY.

在第二次读取时,只处理正确的名称并继续填充名称数组。

After the first and second read, you can read your array NAME-ARRAY.

在第一次和第二次读取之后,您可以读取数组名称数组。

==========================================================================

= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =

There is a problem with both last solutions : you have to know how much lines contains your file. Yep, you can have dynamic programming in cobol too :-)

最后两种解决方案都存在一个问题:您必须知道包含文件的行数。是的,您也可以用cobol进行动态编程:-)

You have to use SORT.

你必须使用排序。

In FILE SECTION add

在文件部分添加

SD  SORT-WORK
01  SORT-RECORD.
    05  SR-ORDER      PIC 9(09).
    05  SR-NAME       PIC X(30).

In your PROCEDURE DIVISION add (in pseude-code, you'll need to add some variables in your working storage section.

在过程分割中添加(在伪代码中,需要在工作存储部分中添加一些变量。

      SORT SORT-WORK
           ASCENDING SORT-ORDER
           INPUT PROCEDURE IS 1000-INPUT
           OUTPUT PROCEDURE IS 2000-OUTPUT

    1000-INPUT SECTION.
         MOVE 0 TO I.
         PERFORM until end-of-file of NAMELIST-FILE-IN  
           ADD 1 TO I
           READ left-name
           MOVE I TO SORT-ORDER
           MOVE left-name TO SR-NAME
    * This operation populates the sort file...
           RELEASE SORT-RECORD
         END-PERFORM.

         PERFORM until end-of-file of NAMELIST-FILE-IN
           ADD 1 TO I
           READ right-name
           MOVE I TO SORT-ORDER
           MOVE right-name TO SR-NAME
    * This operation populates the sort file...
           RELEASE SORT-RECORD     
         END-PERFORM.

         MOVE I TO WS-NB-NAMES.

     2000-OUTPUT SECTION.
         PERFORM VARYING I FROM 1 BY 1 UNTIL I > WS-NB-NAMES
* This operation returns the "next" record. It begins by the first, second...
           RETURN SORT-RECORD
           MOVE SR-NAME TO NAME-LEFT
           RETURN SORT-RECORD
           MOVE SR-NAME TO NAME-RIGHT
           WRITE NAMELIST-FILE-OUT FROM DETAIL-LINE
         END-PERFORM.

You have some example here for SORT

这里有一些排序的例子

Have fun !

玩得开心!