Updated: 11 December 1998 |
OpenVMS Utility Routines Manual
Previous | Contents | Index |
For a sort operation, the arguments to the SOR routines provide SORT with file specifications, key information, and instructions about the sorting process. For a merge operation, the arguments to the SOR routines provide MERGE with the number of input files, input and output file specifications, record information, key information, and input routine information. To perform sort or merge operations, you must pass key information (key_buffer argument) to either the SOR$BEGIN_SORT or SOR$BEGIN_MERGE routine. The key_buffer argument is passed as an array of words. The first word of the array contains the number of keys to be used in the sort or merge. Each block of four words that follows describes one key (multiple keys are listed in order of their priority):
There are both mandatory and optional arguments. The mandatory
arguments appear first in the argument list. You must specify all
arguments in the order in which they are positioned in the argument
list, separating each with a comma. Pass a zero by value to specify any
optional arguments that you are omitting from within the list. You can
end the argument list any time after specifying all the mandatory and
desired optional arguments.
17.2.2 Interfaces to SOR Routines
You can submit data to the SOR routines as complete files or as single records. When your program submits one or more files to SORT or MERGE, which then creates one sorted or merged output file, you are using the file interface. When your program submits records one at a time and then receives the ordered records one at a time, you are using the record interface.
You can combine the file interface with the record interface by submitting files on input and receiving the ordered records on output or by releasing records on input and writing the ordered records to a file on output. Combining the two interfaces provides greater flexibility. If you use the record interface on input, you can process the records before they are sorted; if you use the record interface on output, you can process the records after they are sorted.
The SOR routines used and the order in which they are called depend on
the type of interface used in a sorting or merging operation. The
following sections detail the calling sequence for each of the
interfaces.
17.2.2.1 Sort Operation Using File Interface
For a sort operation using the file interface, pass the input and output file specifications to SORT by calling SOR$PASS_FILES. You must call SOR$PASS_FILES for each input file specification. Pass the output file specification in the first call. If no input files are specified before the call to SOR$BEGIN_SORT, the record interface is used for input; if no output file is specified, the record interface is used for output.
Next, call SOR$BEGIN_SORT to pass instructions about keys and sort options. At this point, you must indicate whether you want to use your own key comparison routine. (This feature is not currently supported by the high-performance Sort/Merge utility.) SORT automatically generates a key comparison routine that is efficient for key data types; however, you might want to provide your own comparison routine to handle special sorting requirements. (For example, you might want names beginning with "Mc" and "Mac" to be placed together.) If you use your own key comparison routine, you must pass its address with the user_compare argument.
Call SOR$SORT_MERGE to execute the sort and direct the sorted records
to the output file. Finally, call SOR$END_SORT to end the sort and
release resources. The SOR$END_SORT routine can be called at any time
to abort a sort or to merge and release all resources allocated to the
sort or merge process.
17.2.2.2 Sort Operation Using Record Interface
For a sort operation using the record interface, first call SOR$BEGIN_SORT. As in the file interface, this routine sets up work areas and passes arguments that define keys and sort options. Note that, if you use the record interface, you must use a record-sorting process (not a tag, address, or index process).
Next, call SOR$RELEASE_REC to release a record to SORT. Call SOR$RELEASE_REC once for each record to be released. After all records have been passed to SORT, call SOR$SORT_MERGE to perform the sorting.
After the sort has been performed, call SOR$RETURN_REC to return a
record from the sort operation. Call this routine once for each record
to be returned. Finally, call the last routine, SOR$END_SORT, to
complete the sort operation and release resources.
17.2.2.3 Merge Operation Using File Interface
For a merge operation using the file interface, pass the input and output file specifications to MERGE by calling SOR$PASS_FILES. You can merge up to 10 input files. (The high-performance Sort/Merge utility allows you to merge up to 12 input files.) by calling SOR$PASS_FILES once for each file. Pass the file specification for the merged output file in the first call. If no input files are specified before the call to SOR$BEGIN_MERGE, the record interface is used for input; if no output file is specified, the record interface is used for output.
Next, to execute the merge, call SOR$BEGIN_MERGE to pass key
information and merge options. At this point, you must indicate whether
you want to use your own key comparison routine tailored to your data.
(This feature is not currently supported by the high-performance
Sort/Merge utility.) Finally, call SOR$END_SORT to release resources.
17.2.2.4 Merge Operation Using Record Interface
For a merge operation using the record interface, first call SOR$BEGIN_MERGE. As in the file interface, this routine passes arguments that define keys and merge options. It also issues the first call to the input routine, which you must create, to begin releasing records to the merge.
Next, call SOR$RETURN_REC to return the merged records to your program. You must call this routine once for each record to be returned. SOR$RETURN_REC continues to call the input routine. MERGE, unlike SORT, does not need to hold all the records before it can begin returning them in the desired order. Releasing, merging, and returning records all take place in this phase of the merge.
Finally, after all the records have been returned, call the last
routine, SOR$END_SORT, to clean up and release resources.
17.2.3 Reentrancy
The SOR routines are reentrant; that is, a number of sort or merge operations can be active at the same time. Thus, a program does not need to finish one sort or merge operation before beginning another. For example, reentrancy lets you perform multiple sorts on a file such as a mailing list and to create several output files, one with the records sorted by name, another sorted by state, another sorted by zip code, and so on.
The context argument, which can optionally be passed with any of the SOR routines, distinguishes among multiple sort or merge operations. When using multiple sort or merge operations, the context argument is required. On the first call, the context longword must be zero. It is then set (by SORT/MERGE) to a value identifying the sort or merge operation. Additional calls to the same sort or merge operation must pass the same context longword. The SOR$END_SORT routine clears the context longword.
17.3 Using the SOR Routines: Examples
This section provides examples of using the SOR routines for various
operations including the following:
Example 17-1 Using SOR Routines to Perform a Merge Using Record Interface in a DEC Fortran Program |
---|
Fortran Program C... C... This program demonstrates the Fortran calling sequences C... for the merge record interface. C... C C THE INPUT FILES ARE LISTED BELOW. C C INFILE1.DAT C C 1 BBBBBBBBBB REST OF DATA IN RECORD................................END OF RECORD C 2 UUUUUUUUUU REST OF DATA IN RECORD................................END OF RECORD C C INFILE2.DAT C C 1 AAAAAAAAAA REST OF DATA IN RECORD................................END OF RECORD C 2 TTTTTTTTTT REST OF DATA IN RECORD................................END OF RECORD C C INFILE3.DAT C C 1 TTTTTTTTTT REST OF DATA IN RECORD................................END OF RECORD C 2 BBBBBBBBBB REST OF DATA IN RECORD................................END OF RECORD C C FOROUT.DAT C C 1 AAAAAAAAAA REST OF DATA IN RECORD................................END OF RECORD C 1 BBBBBBBBBB REST OF DATA IN RECORD................................END OF RECORD C 1 TTTTTTTTTT REST OF DATA IN RECORD................................END OF RECORD C 2 BBBBBBBBBB REST OF DATA IN RECORD................................END OF RECORD C 2 TTTTTTTTTT REST OF DATA IN RECORD................................END OF RECORD C 2 UUUUUUUUUU REST OF DATA IN RECORD................................END OF RECORD C C C................................................................................. C C IMPLICIT INTEGER (A-Z) CHARACTER*80 REC ! A record. EXTERNAL READ_REC ! Routine to read a record. EXTERNAL KOMPAR ! Routine to compare records. EXTERNAL SS$_ENDOFFILE ! System end-of-file value INTEGER*4 SOR$BEGIN_MERGE ! SORT/MERGE function names INTEGER*4 SOR$RETURN_REC INTEGER*4 SOR$END_SORT INTEGER*4 ISTAT ! storage for SORT/MERGE function value INTEGER*4 LENGTH ! length of the returned record INTEGER*2 LRL ! Longest Record Length (LRL) LOGICAL*1 ORDER ! #files to merge (merge order) DATA ORDER,LRL/3,80/ ! Order of the merge=3,LRL=80 C... C... First open all the input files. C... OPEN (UNIT=10, FILE='INFILE1.DAT',TYPE='OLD',READONLY, * FORM='FORMATTED') OPEN (UNIT=11, FILE='INFILE2.DAT',TYPE='OLD',READONLY, * FORM='FORMATTED') OPEN (UNIT=12, FILE='INFILE3.DAT',TYPE='OLD',READONLY, * FORM='FORMATTED') C C... Open the output file. C OPEN (UNIT=8, FILE='TEMP.TMP', TYPE='NEW') C... C... Initialize the merge. Pass the merge order, the largest C... record length, the compare routine address, and the C... input routine address. C... ISTAT = SOR$BEGIN_MERGE (,LRL,,ORDER, * KOMPAR,,READ_REC) IF (.NOT. ISTAT) GOTO 10 ! Check for error. C... C... Now loop getting merged records. SOR$RETURN_REC will C... call READ_REC when it needs input. C... 5 ISTAT = SOR$RETURN_REC (REC, LENGTH) IF (ISTAT .EQ. %LOC(SS$_ENDOFFILE)) GO TO 30 ! Check for end of file. IF (.NOT. ISTAT) GO TO 10 ! Check for error. WRITE(8,200) REC ! Output the record. 200 FORMAT(' ',A) GOTO 5 ! And loop back. C... C... Now tell SORT that we are all done. C... 30 ISTAT = SOR$END_SORT() IF (.NOT. ISTAT) GOTO 10 ! Check for error. CALL EXIT C... C... Here if an error occurred. Write out the error status C... and exit. C... 10 WRITE(8,201)ISTAT 201 FORMAT(' ?ERROR CODE', I20) CALL EXIT END FUNCTION READ_REC (RECX, FILE, SIZE) C... C... This routine reads a record from one of the input files C... for merging. It will be called by SOR$BEGIN_MERGE and by C... SOR$RETURN_REC. C... Parameters: C... C... RECX.wcp.ds character buffer to hold the record after C... it is read in. C... C... FILE.rl.r indicates which file the record is C... to be read from. 1 specifies the C... first file, 2 specifies the second C... etc. C... C... LENGTH.wl.r is the actual number of bytes in C... the record. This is set by READ_REC. C... IMPLICIT INTEGER (A-Z) PARAMETER MAXFIL=10 ! Max number of files. EXTERNAL SS$_ENDOFFILE ! End of file status code. EXTERNAL SS$_NORMAL ! Success status code. LOGICAL*1 FILTAB(MAXFIL) CHARACTER*(80) RECX ! MAX LRL =80 DATA FILTAB/10,11,12,13,14,15,16,17,18,19/ ! Table of I/O unit numbers. READ_REC = %LOC(SS$_ENDOFFILE) ! Give end of file return IF (FILE .LT. 1 .OR. FILE .GT. MAXFIL) RETURN ! if illegal call. READ (FILTAB(FILE), 100, ERR=75, END=50) RECX ! Read the record. 100 FORMAT(A) READ_REC = %LOC(SS$_NORMAL) ! Return success code. SIZE = LEN (RECX) ! Return size of record. RETURN C... Here if end of file. 50 READ_REC = %LOC(SS$_ENDOFFILE) ! Return "end of file" code. RETURN C... Here if error while reading 75 READ_REC = 0 SIZE = 0 RETURN END FUNCTION KOMPAR (REC1,REC2) C... C... This routine compares two records. It returns -1 C... if the first record is smaller than the second, C... 0 if the records are equal, and 1 if the first record C... is larger than the second. C... PARAMETER KEYSIZ=10 IMPLICIT INTEGER (A-Z) LOGICAL*1 REC1(KEYSIZ),REC2(KEYSIZ) DO 20 I=1,KEYSIZ KOMPAR = REC1(I) - REC2(I) IF (KOMPAR .NE. 0) GOTO 50 20 CONTINUE RETURN 50 KOMPAR = ISIGN (1, KOMPAR) RETURN END |
Example 17-2 is a DEC Fortran program that demonstrates a sort operation using a file interface on input and a record interface on output.
Example 17-2 Using SOR Routines to Sort Using Mixed Interface in a DEC Fortran Program |
---|
Program PROGRAM CALLSORT C C C This is a sample Fortran program that calls the SOR C routines using the file interface for input and the C record interface for output. This program requests C a record sort of the file 'R010SQ.DAT' and writes C the records to SYS$OUTPUT. The key is an 80-byte C character ascending key starting in position 1 of C each record. C C A short version of the input and output files follows: C C Input file R010SQ.DAT C 1 BBBBBBBBBB REST OF DATA IN RECORD................................END OF RECORD C 2 UUUUUUUUUU REST OF DATA IN RECORD................................END OF RECORD C 1 AAAAAAAAAA REST OF DATA IN RECORD................................END OF RECORD C 2 TTTTTTTTTT REST OF DATA IN RECORD................................END OF RECORD C 1 TTTTTTTTTT REST OF DATA IN RECORD................................END OF RECORD C 2 BBBBBBBBBB REST OF DATA IN RECORD................................END OF RECORD C 1 QQQQQQQQQQ REST OF DATA IN RECORD................................END OF RECORD C 2 AAAAAAAAAA REST OF DATA IN RECORD................................END OF RECORD C 1 UUUUUUUUUU REST OF DATA IN RECORD................................END OF RECORD C 2 QQQQQQQQQQ REST OF DATA IN RECORD................................END OF RECORD C C Output file SYS$OUTPUT C C 1 AAAAAAAAAA REST OF DATA IN RECORD...............................END OF RECORD C 1 BBBBBBBBBB REST OF DATA IN RECORD...............................END OF RECORD C 1 QQQQQQQQQQ REST OF DATA IN RECORD...............................END OF RECORD C 1 TTTTTTTTTT REST OF DATA IN RECORD...............................END OF RECORD C 1 UUUUUUUUUU REST OF DATA IN RECORD...............................END OF RECORD C 2 AAAAAAAAAA REST OF DATA IN RECORD...............................END OF RECORD C 2 BBBBBBBBBB REST OF DATA IN RECORD...............................END OF RECORD C 2 QQQQQQQQQQ REST OF DATA IN RECORD...............................END OF RECORD C 2 TTTTTTTTTT REST OF DATA IN RECORD...............................END OF RECORD C 2 UUUUUUUUUU REST OF DATA IN RECORD...............................END OF RECORD C C----------------------------------------------------------------------------- C C Define external functions and data. C CHARACTER*80 RECBUF CHARACTER*10 INPUTNAME !Input file name INTEGER*2 KEYBUF(5) !Key definition buffer INTEGER*4 SOR$PASS_FILES !SORT function names INTEGER*4 SOR$BEGIN_SORT INTEGER*4 SOR$SORT_MERGE INTEGER*4 SOR$RETURN_REC INTEGER*4 SOR$END_SORT INTEGER*4 ISTATUS !Storage for SORT function value EXTERNAL SS$_ENDOFFILE EXTERNAL DSC$K_DTYPE_T EXTERNAL SOR$GK_RECORD INTEGER*4 SRTTYPE C C Initialize data -- first the file names, then the key buffer for C one 80-byte character key starting in position 1, 3 work files, C and a record sort process. C DATA INPUTNAME/'R010SQ.DAT'/ KEYBUF(1) = 1 KEYBUF(2) = %LOC(DSC$K_DTYPE_T) KEYBUF(3) = 0 KEYBUF(4) = 0 KEYBUF(5) = 80 SRTTYPE = %LOC(SOR$GK_RECORD) C C Call the SORT -- each call is a function. C C C Pass SORT the file names. C ISTATUS = SOR$PASS_FILES(INPUTNAME) IF (.NOT. ISTATUS) GOTO 10 C C Initialize the work areas and keys. C ISTATUS = SOR$BEGIN_SORT(KEYBUF,,,,,,SRTTYPE,%REF(3)) IF (.NOT. ISTATUS) GOTO 10 C C Sort the records. C ISTATUS = SOR$SORT_MERGE( ) IF (.NOT. ISTATUS) GOTO 10 C C Now retrieve the individual records and display them. C 5 ISTATUS = SOR$RETURN_REC(RECBUF) IF (.NOT. ISTATUS) GOTO 6 ISTATUS = LIB$PUT_OUTPUT(RECBUF) GOTO 5 6 IF (ISTATUS .EQ. %LOC(SS$_ENDOFFILE)) GOTO 7 GOTO 10 C C Clean up the work areas and files. C 7 ISTATUS = SOR$END_SORT() IF (.NOT. ISTATUS) GOTO 10 STOP 'SORT SUCCESSFUL' 10 STOP 'SORT UNSUCCESSFUL' END |
Example 17-3 is a DEC Pascal program that demonstrates a merge operation using a file interface.
Example 17-3 Using SOR Routines to Merge Three Input Files in a DEC Pascal Program |
---|
Program (* This program merges three input files, (IN_FILE.DAT, IN_FILE2.DAT IN_FILE3.DAT), and creates one merged output file. *) program mergerecs( output, in_file1, in_file2, in_file3, out_file ); CONST SS$_NORMAL = 1; SS$_ENDOFFILE = %X870; SOR$GK_RECORD = 1; SOR$M_STABLE = 1; SOR$M_SEQ_CHECK = 4; SOR$M_SIGNAL = 8; DSC$K_DTYPE_T = 14; TYPE $UBYTE = [BYTE] 0..255; $UWORD = [WORD] 0..65535; const num_of_keys = 1; merge_order = 3; lrl = 131; ascending = 0; descending = 1; type key_buffer_block= packed record key_type: $uword; key_order: $uword; key_offset: $uword; key_length: $uword; end; key_buffer_type= packed record key_count: $uword; blocks: packed array[1..num_of_keys] of key_buffer_block; end; record_buffer = packed array[1..lrl] of char; record_buffer_descr = packed record length: $uword; dummy: $uword; addr: ^record_buffer; end; var in_file1, in_file2, in_file3, out_file: text; key_buffer: key_buffer_type; rec_buffer: record_buffer; rec_length: $uword; status: integer; i: integer; function sor$begin_merge( var buffer: key_buffer_type; lrl: $uword; mrg_options: integer; merge_order: $ubyte; %immed cmp_rtn: integer := 0; %immed eql_rtn: integer := 0; %immed [unbound] function read_record( var rec: record_buffer_descr; var filenumber: integer; var recordsize: $uword): integer ): integer; extern; function sor$return_rec( %stdescr rec: record_buffer; var rec_size: $uword ): integer; extern; function sor$end_sort: integer; extern; procedure sys$exit( %immed status : integer ); extern; function read_record( var rec: record_buffer_descr; var filenumber: integer; var recordsize: $uword ): integer; procedure readone( var filename: text ); begin recordsize := 0; if eof(filename) then read_record := ss$_endoffile else begin while not eoln(filename) and (recordsize < rec.length) do begin recordsize := recordsize + 1; read(filename,rec.addr^[recordsize]); end; readln(filename); end; end; begin read_record := ss$_normal; case filenumber of 1: readone(in_file1); 2: readone(in_file2); 3: readone(in_file3); otherwise read_record := ss$_endoffile; end; end; procedure initfiles; begin open( in_file1, 'infile1.dat', old ); open( in_file2, 'infile2.dat', old ); open( in_file3, 'infile3.dat', old ); open( out_file, 'temp.tmp' ); reset( in_file1 ); reset( in_file2 ); reset( in_file3 ); rewrite( out_file ); end; procedure error( status : integer ); begin writeln( 'merge unsuccessful. status=%x', status:8 hex ); sys$exit(status); end; begin with key_buffer do begin key_count := 1; with blocks[1] do begin key_type := dsc$k_dtype_t; key_order := ascending; key_offset := 0; key_length := 5; end; end; initfiles; status := sor$begin_merge( key_buffer, lrl, sor$m_seq_check + sor$m_signal, merge_order, 0, 0, read_record ); repeat begin rec_length := 0; status := sor$return_rec( rec_buffer, rec_length ); if odd(status) then begin for i := 1 to rec_length do write(out_file, rec_buffer[i]); writeln(out_file); end; end until not odd(status); if status <> ss$_endoffile then error(status); status := sor$end_sort; if not odd(status) then error(status); writeln( 'merge successful.' ); end. |
Example 17-4 is a DEC Pascal program that demonstrates a sort operation using a record interface.
Example 17-4 Using SOR Routines to Sort Records from Two Input Files in a DEC Pascal Program |
---|
Pascal Program PROGRAM FILETORECORDSORT (OUTPUT,SORTOUT); (* This program calls SOR routines to read and sort records from two input files, (PASINPUT1.DAT and PASINPUT2.DAT) and to return sorted records to this program to be written to the output file, (TEMP.TMP). *) (* Declarations for external status codes, and data structures, such as the types $UBYTE (an unsigned byte) and $UWORD (an unsigned word). *) CONST SS$_NORMAL = 1; SS$_ENDOFFILE = %X870; SOR$GK_RECORD = 1; SOR$M_STABLE = 1; SOR$M_SEQ_CHECK = 4; SOR$M_SIGNAL = 8; DSC$K_DTYPE_T = 14; TYPE $UBYTE = [BYTE] 0..255; $UWORD = [WORD] 0..65535; CONST Numberofkeys = 1 ; (* Number of keys for this sort *) LRL = 131 ; (* Longest Record Length for output records *) (* Key orders *) Ascending = 0 ; Descending = 1 ; TYPE Keybufferblock= packed record Keytype : $UWORD ; Keyorder : $UWORD ; Keyoffset : $UWORD ; Keylength : $UWORD end ; (* The keybuffer. Note that the field buffer is a one-component array in this program. This type definition would allow a multikeyed sort. *) Keybuffer= packed record Numkeys : $UWORD ; Blocks : packed array[1..Numberofkeys] OF Keybufferblock end ; (* The record buffer. This buffer will be used to hold the returned records from SORT. *) Recordbuffer = packed array[1..LRL] of char ; (* Name type for input and output files. A necessary fudge for %stdescr mechanism. *) nametype= packed array[1..13] of char ; VAR Sortout : text ; (* the output file *) Buffer : Keybuffer ; (* the actual keybuffer *) Sortoptions : integer ; (* flag for sorting options *) Sorttype : $UBYTE ; (* sorting process *) Numworkfiles : $UBYTE ; (* number of work files *) Status : integer ; (* function return status code *) Rec : Recordbuffer ; (* a record buffer *) Recordlength : $UWORD ; (* the returned record length *) Inputname: nametype ; (* input file name *) i : integer ; (* loop control variable *) (* function and procedure declarations *) (* Declarations of SORT functions *) (* Note that the following SORT routine declarations do not use all of the possible routine parameters. *) (* The parameters used MUST have all preceding parameters specified, however. *) FUNCTION SOR$PASS_FILES (%STDESCR Inname : nametype ) : INTEGER ; EXTERN ; FUNCTION SOR$BEGIN_SORT( VAR Buffer : Keybuffer ; Lrlen : $UWORD ; VAR Sortoptions : INTEGER ; %IMMED Filesize : INTEGER ; %IMMED Usercompare : INTEGER ; %IMMED Userequal : INTEGER ; VAR Sorttype : $UBYTE ; VAR Numworkfiles : $UBYTE ) : INTEGER ; EXTERN ; FUNCTION SOR$SORT_MERGE : INTEGER ; EXTERN ; FUNCTION SOR$RETURN_REC( %STDESCR Rec : Recordbuffer ; VAR Recordsize : $UWORD ) : INTEGER ; EXTERN ; FUNCTION SOR$END_SORT : INTEGER ; EXTERN ; (* End of the SORT function declarations *) (* The CHECKSTATUS routine checks the return status for errors. *) (* If there is an error, write an error message and exit via sys$exit *) PROCEDURE CHECKSTATUS( var status : integer ) ; procedure sys$exit( status : integer ) ; extern ; begin (* begin checkstatus *) if odd(status) then begin writeln( ' SORT unsuccessful. Error status = ', status:8 hex ) ; SYS$EXIT( status ) ; end ; end ; (* end checkstatus *) (* end function and routine declarations *) BEGIN (* begin the main routine *) (* Initialize data for one 8-byte character key, starting at record offset 0, 3 work files, and the record sorting process *) Inputname := 'PASINPUT1.DAT' ; WITH Buffer DO BEGIN Numkeys := 1; WITH Blocks[1] DO BEGIN Keytype := DSC$K_DTYPE_T ; (* Use OpenVMS descriptor data types to define SORT data types. *) Keyorder := Ascending ; Keyoffset := 0 ; Keylength := 8 ; END; END; Sorttype := SOR$GK_RECORD ; (* Use the global SORT constant to define the sort process. *) Sortoptions := SOR$M_STABLE ; (* Use the global SORT constant to define the stable sort option. *) Numworkfiles := 3 ; (* call the sort routines as a series of functions *) (* pass the first filename to SORT *) Status := SOR$PASS_FILES( Inputname ) ; (* Check status for error. *) CHECKSTATUS( Status ) ; (* pass the second filename to SORT *) Inputname := 'PASINPUT2.DAT' ; Status := SOR$PASS_FILES( Inputname ) ; (* Check status for error. *) CHECKSTATUS( Status ) ; (* initialize work areas and keys *) Status := SOR$BEGIN_SORT( Buffer, 0, Sortoptions, 0, 0, 0, Sorttype, Numworkfiles ) ; (* Check status for error. *) CHECKSTATUS( Status ) ; (* sort the records *) Status := SOR$SORT_MERGE ; (* Check status for error. *) CHECKSTATUS( Status ) ; (* Ready output file for writing returned records from SORT. *) OPEN( SORTOUT, 'TEMP.TMP' ) ; REWRITE( SORTOUT ) ; (* Now get the sorted records from SORT. *) Recordlength := 0 ; REPEAT Status := SOR$RETURN_REC( Rec, Recordlength ) ; if odd( Status ) then (* if successful, write record to output file. *) begin for i := 1 to Recordlength do write( sortout, Rec[i] ) ; (* write each character *) writeln (sortout) ; (* end output line *) end; UNTIL not odd( Status ) ; (* If there was just no more data to be returned (eof) continue, otherwise exit with an error. *) if Status <> SS$_ENDOFFILE then CHECKSTATUS( Status ) ; (* The sort has been successful to this point. *) (* Close the output file *) CLOSE( sortout ) ; (* clean up work areas and files *) Status := SOR$END_SORT ; (* Check status for error. *) CHECKSTATUS( Status ); WRITELN ('SORT SUCCESSFUL') ; END. |
Previous | Next | Contents | Index |
Copyright © Compaq Computer Corporation 1998. All rights reserved. Legal |
4493PRO_050.HTML
|