How to use pointers in PL1 programming language

I am trying to learn the use of pointers in PL1. However below approach is not working

  DCL MYPTR PTR;                               
    DCL MYVAR CHAR(10) INIT('1234567890');       
    PUT SKIP(2) LIST('DISPLAY MYVAR: ',MYVAR);   
    MYPTR = ADDR(MYVAR);                             
    PUT SKIP(2) LIST('DISPLAY MYPTR: ',MYPTR);  

OUTPUT:

 DISPLAY MYVAR:          1234567890               
                                                 
DISPLAY MYPTR:                                   

Upvotes: 0

Views: 1478

Answers (1)

phunsoft
phunsoft

Reputation: 2745

Pointers are variables that contain a storage address. You use them to remap a storage area with different layout. For example, assume you've got records in a single data set that have different layout, say:

dcl 1 RecordType1,
      2 RecType        char( 01 ),
      2 Field01        char( 10 ),
      2 Field02        char( 20 ),
      2 Number01       decimal packed( 10,2 ),
      2 Field03        char( 10 );

dcl 1 RecordType2,
      2 RecType        char( 01 ),
      2 Field01        char( 05 ),
      2 *              char( 02 ), 
      2 Number01       bin fixed( 31 ),
      2 Numner02       bin fixed( 31 ),
      2 Field02        char( 100 );

These declarations set aside two distinct storage areas, one for each type. Note that the records have different lengths. How would you read in the records, if you only know the type, and with this the length after having read the record? You would need to do something like:

  • reading into an area long enough for the longest type,
  • check the type,
  • move to the structure according to the type
  • process the individual fields.

This involves a lot of unnecessary data moves.

Using pointers, and the associated based() attribute in declarations, you can define the structures as mapping, i.e. witout underlying storage. You then use a single pointer for all mappings.

dcl 1 RecordType1      based( pRecord ),
      2 RecType        char( 01 ),
      2 Field01        char( 10 ),
      2 Field02        char( 20 ),
      2 Number01       decimal packed( 10,2 ),
      2 Field03        char( 10 );

dcl 1 RecordType2      based( pRecord ),
      2 *              char( 01 ),
      2 Field01        char( 05 ),
      2 *              char( 02 ), 
      2 Number01       bin fixed( 31 ),
      2 Numner02       bin fixed( 31 ),
      2 Field02        char( 100 );

dcl pRecord            prt;
dcl LongestRecord      char( 116 );

pRecord = addr( LongestRecord );

Now, you do something like this:

  • read the record into the LongestRecord field,
  • test the type by inspecting the type field RecType (assuming the type indicator is at the same position for each type).
  • Access the individual files via qualified variable reference, e.g. RecordType1.Field01, or RecordType2.Number02

No more unnecessary data moves from input area to mapping area..

If you read the records from a data set, you can even avoid the first move and access the records directly in the input buffer; just tell the read statement to set the pointer, instead of moving the data into the LongestRecord field:

dcl fInput             external file record input;
...
read file( fInput ) set( pRecord );

You can now drop the declaration for the LongestRecord variable, and the statement setting pRecord to the address of that variable.

For completeness, only: PL/I offers another way to map a storage area with two or more different layouts: UNION, but this is not the question here.

Upvotes: 3

Related Questions