• The Four Hundred
  • Subscribe
  • Media Kit
  • Contributors
  • About Us
  • Contact
Menu
  • The Four Hundred
  • Subscribe
  • Media Kit
  • Contributors
  • About Us
  • Contact
  • Guru: Fall Brings New RPG Features, Part 2

    January 11, 2021 Jon Paris

    In my previous tip I outlined some of the new features added to RPG with the Fall 2020 release. In this and the following tip I will be covering the features that I ran out of space for in that first one.

    This time I will cover the new FOR-EACH loop construct. I have wanted this in RPG ever since encountering it in PHP. Simply put, it automatically iterates through an array, “serving up” one element at a time. When I say “an array” I mean any kind of array, including data structure arrays, dynamic arrays and even the new temporary arrays created by the %LIST BIF that I mentioned in the previous tip.

    Here’s a really simple example of using FOR-EACH to process all of the elements in a simple standalone array:

    dcl-s  nameArray  char(10)  Dim(100);
    dcl-s  name       like(nameArray);
    
    // The old way
    For element = 1 to %elem(nameArray);
       Dsply  nameArray(element);
    EndFor;
    
    // The For-Each way
    For-Each  name in nameArray;
       Dsply name;
    EndFor;
    

    Notice that because FOR-EACH extracts each element into the name field, we don’t need to use a subscript to access the element within the loop. Not that big a deal when processing a simple array, but it makes life a lot simpler when dealing with a multi-field DS array. You’ll see an example of this in a moment.

    Where FOR-EACH really shines, though, is when working with the new dynamically sized arrays. Because RPG knows how many active elements are in the array, it is able to use that information to control the operation of the loop.

    One of my favorite uses of the new dynamic array support is for handling SQL result sets, so I’ll use SQL for this next example. What I love is that the combination of the dynamic array and FOR-EACH means that I don’t actually have to use the SQLERRD(3) value to control the loop. Here’s my simple example.

    Dcl-Ds  results  ExtName('ANIMALS')  qualified  dim( *Auto : 1000 ) End-ds;
    Dcl-Ds  animal  likeDs(results);
    
    Dcl-s  type  like(results.TYPE);
    
    Dsply ( 'What type of animal do you want?' ) ' ' type;
    
    Exec SQL
         Declare animalsCursor cursor for
            Select * from ANIMALS where type = :type;
    
    Exec SQL
         Open animalsCursor;
    
    Exec SQL
         Fetch from animalsCursor for 1000 rows into :results;
    
    Dsply ( 'Found ' + %Char( %Elem( results ) ) + ' matching animals' );
    
    For-Each animal in results;
       Dsply ( 'Id: ' + %Char(animal.Id) + ' - Name: ' + animal.name );
    EndFor;
    
    

    You can also see here what I meant by simplified field references. Had I coded the loop manually, references such as animal.Id and animal.name would have needed to be coded as results(element).Id and results(element).name. More typing and less elegant.

    For me though, this is not just a reduction in typing. It also increases the readability in the sense that the intent of my code is more obvious, i.e., I am going to process every active element in this array.

    Now that you’ve seen how much easier this combination can make processing SQL just imagine how much better still it would be if we didn’t have to worry about having to use a cursor. Wouldn’t it be nice just to do a multi-row SELECT into the target DS? That would be so much easier and closer to what happens in other languages. It just so happens that I am not the only one who feels this way, and there is an RFE out there requesting that IBM provide this functionality. IBM do pay a lot of attention to the number of votes that requests like this receive so, if you agree with me, won’t you join me in voting for this enhancement? You’ll find it at https://www.ibm.com/developerworks/rfe/execute?use_case=viewRfe&CR_ID=141665.

    Is FOR-EACH A Good Fit For All Your Array-Processing Needs?

    As you have seen, FOR-EACH works beautifully when processing all the elements of an array and in particular, when processing a dynamic array. But what about a traditional (i.e., fixed-sized) RPG array that has not been filled? Prior to the advent of FOR-EACH we would normally code this in a regular FOR loop, using the highest active element number as the upper limit. We can use FOR-EACH in such situations, but it requires that we use %SUBARR to limit the scope of the array and the resulting code is not quite so elegant. As a result, I suspect I may still use the old approach in such situations, but take a look at the comparison example below and form your own opinion.

    // Traditional FOR loop approach
    For element = 1 to nameCount;
       Dsply nameArray(element);
    EndFor;
    
    // Using FOR-EACH with a partially filled array
    For-each name in %Subarr(nameArray: 1: nameCount);
       Dsply name;
    Endfor;  
    

    Next Time

    In my third and final tip on these enhancements, I will be taking a look at a couple of new compiler options designed to aid in conversions from character to numeric. You’ll see that not only do they improve the operation of BIFs such as %DEC, but also aid in processing XML and JSON.

    Jon Paris is one of the world’s foremost experts on programming on the IBM i platform. A frequent author, forum contributor, and speaker at User Groups and technical conferences around the world, he is also an IBM Champion and a partner at Partner400 and System i Developer. He hosts the RPG & DB2 Summit with partners Susan Gantner and Paul Tuohy.

    RELATED STORIES

    Fall Brings New RPG Features

    7.4 Brings New RPG Goodies

    Guru: Dynamic Arrays Come To RPG

    Dynamic Arrays Come To RPG – The Next Part Of The Story

    Dynamic Arrays Come To RPG – Limitations, Circumventions, And More

    Share this:

    • Reddit
    • Facebook
    • LinkedIn
    • Twitter
    • Email

    Tags: Tags: 400guru, dynamically sized arrays, FHG, Four Hundred Guru, IBM i, JSON, RFE, RPG, XML

    Sponsored by
    WorksRight Software

    Do you need area code information?
    Do you need ZIP Code information?
    Do you need ZIP+4 information?
    Do you need city name information?
    Do you need county information?
    Do you need a nearest dealer locator system?

    We can HELP! We have affordable AS/400 software and data to do all of the above. Whether you need a simple city name retrieval system or a sophisticated CASS postal coding system, we have it for you!

    The ZIP/CITY system is based on 5-digit ZIP Codes. You can retrieve city names, state names, county names, area codes, time zones, latitude, longitude, and more just by knowing the ZIP Code. We supply information on all the latest area code changes. A nearest dealer locator function is also included. ZIP/CITY includes software, data, monthly updates, and unlimited support. The cost is $495 per year.

    PER/ZIP4 is a sophisticated CASS certified postal coding system for assigning ZIP Codes, ZIP+4, carrier route, and delivery point codes. PER/ZIP4 also provides county names and FIPS codes. PER/ZIP4 can be used interactively, in batch, and with callable programs. PER/ZIP4 includes software, data, monthly updates, and unlimited support. The cost is $3,900 for the first year, and $1,950 for renewal.

    Just call us and we’ll arrange for 30 days FREE use of either ZIP/CITY or PER/ZIP4.

    WorksRight Software, Inc.
    Phone: 601-856-8337
    Fax: 601-856-9432
    Email: software@worksright.com
    Website: www.worksright.com

    Share this:

    • Reddit
    • Facebook
    • LinkedIn
    • Twitter
    • Email

    More Vintage Power Systems Feature Withdrawals Thoroughly Modern: DevOps Refactoring Of RPG Applications with RDi

    3 thoughts on “Guru: Fall Brings New RPG Features, Part 2”

    • Rick says:
      January 11, 2021 at 8:44 am

      Couldn’t find your RFE 141665 to vote. Great article!

      Reply
    • sAM says:
      January 11, 2021 at 12:19 pm

      I could not get this link to work:

      IBM do pay a lot of attention to the number of votes that requests like this receive so, if you agree with me, won’t you join me in voting for this enhancement? You’ll find it at https://www.ibm.com/developerworks/rfe/execute?use_case=viewRfe&CR_ID=141665.

      Reply
    • Sam says:
      January 11, 2021 at 12:43 pm

      I found the RFE by searching by the id, 141665. However, it is marked as “Declined”.

      Reply

    Leave a Reply Cancel reply

TFH Volume: 31 Issue: 2

This Issue Sponsored By

  • Profound Logic Software
  • Fresche Solutions
  • CYBRA
  • Computer Keyes
  • WorksRight Software

Table of Contents

  • Seiden Group Unveils A PHP Distro For IBM i
  • Thoroughly Modern: DevOps Refactoring Of RPG Applications with RDi
  • Guru: Fall Brings New RPG Features, Part 2
  • More Vintage Power Systems Feature Withdrawals
  • IBM i PTF Guide, Volume 23, Number 1

Content archive

  • The Four Hundred
  • Four Hundred Stuff
  • Four Hundred Guru

Recent Posts

  • Meet The Next Gen Of IBMers Helping To Build IBM i
  • Looks Like IBM Is Building A Linux-Like PASE For IBM i After All
  • Will Independent IBM i Clouds Survive PowerVS?
  • Now, IBM Is Jacking Up Hardware Maintenance Prices
  • IBM i PTF Guide, Volume 27, Number 24
  • Big Blue Raises IBM i License Transfer Fees, Other Prices
  • Keep The IBM i Youth Movement Going With More Training, Better Tools
  • Remain Begins Migrating DevOps Tools To VS Code
  • IBM Readies LTO-10 Tape Drives And Libraries
  • IBM i PTF Guide, Volume 27, Number 23

Subscribe

To get news from IT Jungle sent to your inbox every week, subscribe to our newsletter.

Pages

  • About Us
  • Contact
  • Contributors
  • Four Hundred Monitor
  • IBM i PTF Guide
  • Media Kit
  • Subscribe

Search

Copyright © 2025 IT Jungle