Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations bkrike on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

for loop within a while loop does not execute 1

Status
Not open for further replies.

jcarrott

Programmer
May 28, 2009
130
US
I have a input file that has ~ for segment seperators and ^ for data seperators within the segment.
The first 9 segments are processed in order, after the 9th segment the segments available can vary. So I used a for loop. The for loop starts at line 103. The first line within the loop is at line 105. The code never enters thye for loop.
Is Perl able to execute a FOR loop within a WHILE loop?
The link contains both the data and the code.
 
Hi

Please do not put us to sign up on box.net just to see your file.

Reduce your code to the minimum needed to reproduce the error.
( I used to find the bugs this way, while preparing my code to post it one a forum. )


Feherke.
 
I am sorry about that I thought the link was to my code.

Here is the segment 9 that works and the FOR loop that does not work.

# segin[9] is N1 - Ship to name
for ($seqin[9]) {
@line = split(/\^/, $segin[9]);
$st_name = $line[2];
}
#########################################################
# after this point anything can happen
# first characters must be checked until ITD segment
# ITD[1] is used,
# DTM is skipped,
# then loop for IT1 & PID segments till done
#########################################################
# Loop could contain 99 LT1 records, 99 PID records, &
# 9 other records, loop should be set to 210 - a larger
# then possible number. But the current starting point
# is segment 10, so 210 plus 10 is 220.
#########################################################
for ($L1 = 10; $L1 >= 220; $L1++) {
# parse a new line
@temp = split(/\^/, $segin[$L1]);
if ($temp[0] eq "N3") {
$st_add1 = $temp[1];
if ($temp[2]) {
$st_add2 = " ";
}else {
$st_add2 = $temp[2];
}
}
elsif ($temp[0] eq "N4") {
$st_city = $temp[1];
$st_stat = $temp[2];
$st_zip = $temp[3];
}
elsif ($temp[0] eq "ITD") {
$terms = $temp[1];
$dte_code = $temp[2];
$net_days = $temp[7];
}
elsif ($temp[0] eq "DTM") {
$dtm = $segin[1];
}
elsif ($temp[0] eq "IT1") {
$line_nbr = $temp[1];
$qty = $temp[2];
$uom = $temp[3];
$price = $temp[4];
$price_cd = $temp[5];
$ven_item = $temp[7];
$item = $temp[9];
}
elsif ($temp[0] eq "PID") {
$description = $temp[5];
}
elsif ($temp[0] eq "TDS") {
$tot_inv_amt = $temp[1];
}
}
 
Here is a stripped down version of the whole program.

#!/usr/bin/perl -w

#### program variables

$vPath1="D:\\Invoice\\";
$vName1="GHX810.out";

open(X12, "$vPath1$vName1");

while (<X12>) {
@segin = split(/\~/, $_);
# segin[3] is BIG
for ($seqin[3]) {
@line = split(/\^/, $segin[3]);
$company = substr($line[4], 0, 1);
if($company eq 1) {
$company = 120;
} elsif($company eq 7) {
$company = 710;
} elsif($company eq 8) {
$company = 800;
}
$invoice_dte = $line[1];
$invoice = $line[2];
$po_date = $line[3];
$po_number = $line[4];
$x = $line[5];
$y = $line[6];
if ($line[7]) {
$inv_typ = " ";
}else {
$inv_typ = $line[7];
}
}
# segin[9] is N1 - Ship to name
for ($seqin[9]) {
@line = split(/\^/, $segin[9]);
$st_name = $line[2];
}
for ($L1 = 10; $L1 >= 220; $L1++) {
# parse a new line
@temp = split(/\^/, $segin[$L1]);
if ($temp[0] eq "N3") {
$st_add1 = $temp[1];
if ($temp[2]) {
$st_add2 = " ";
}else {
$st_add2 = $temp[2];
}
}
elsif ($temp[0] eq "N4") {
$st_city = $temp[1];
$st_stat = $temp[2];
$st_zip = $temp[3];
}
elsif ($temp[0] eq "ITD") {
$terms = $temp[1];
$dte_code = $temp[2];
$net_days = $temp[7];
}
elsif ($temp[0] eq "DTM") {
$dtm = $segin[1];
}
elsif ($temp[0] eq "IT1") {
$line_nbr = $temp[1];
$qty = $temp[2];
$uom = $temp[3];
$price = $temp[4];
$price_cd = $temp[5];
$ven_item = $temp[7];
$item = $temp[9];
}
elsif ($temp[0] eq "PID") {
$description = $temp[5];
}
elsif ($temp[0] eq "TDS") {
$tot_inv_amt = $temp[1];
}
}
}
close(X12);
 
This is the data for the code. The data is one line

ISA^00^ ^00^ ^01^043645501 ^01^077900207 ^090810^1019^U^00401^973397655^0^P^|~GS^IN^108878828^077900207^20090810^1019^791^X^004010~ST^810^7910004~BIG^20090807^45315897^20090807^1550510^^^DI~PER^BI^CREDIT DEPT^TE^800-426-5772~N1^BT^OCHSNER CLINIC FOUNDATION^91^00007164~N3^ACCOUNTS PAYABLE~N4^NEW ORLEANS^LA^70123~N1^BY^OCHSNER CLINIC FOUNDATION^92^7164~N1^ST^OCHSNER CLINIC NORTHSHORE^92^08978219~ITD^05^3^^20090906^^20090906^30^^^^^NET 30 DAYS~DTM^011^20090807^000000~IT1^1^2^EA^64.76^^VC^7470961~PID^F^^^^NO 9 BLACK TONER CARTRIDGE~TDS^12952~CTT^1~SE^15^7910004~GE^1^791~IEA^1^973397655~
 
you have your whole segin/seqin issues again with this code

Code:
       for ($seqin[9]) {
          @line = split(/\^/, $segin[9]);
          $st_name = $line[2];
       }

for is for looping through arrays.. not sure what your trying to do here.




~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
[noevil]
Travis - Those who say it cannot be done are usually interrupted by someone else doing it; Give the wrong symptoms, get the wrong solutions;
 
I fixed the seqin/segin issue and thank you very much for catching that. That was the reason the first part of the code had an issue.
This part of the code still has a issue.
The input data has 2 seperators, the ~ to seperate segments and the ^ to seperate data within a segment.
The first thing I do is seperate the one line of data into segments. I use the FOR statements to process each of the segments because after the line is split they are sort of in an array.
The issue comes with the FOR loop where I try to loop through the remaining segments. This fails right away.
 
If you could clean up your code and repost and and point out where you are having problems it would help.
all those lines where you have


for ($var[0]) { }


can be removed as they aren't doing anything

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
[noevil]
Travis - Those who say it cannot be done are usually interrupted by someone else doing it; Give the wrong symptoms, get the wrong solutions;
 
I ran the code in debug mode within Perl Express, and the code:
for ($var[0]) { }
does trap and process the correct segment.

Here is the current version of the code.

#!/usr/bin/perl -w

#### program variables

$vPath1="D:\\Invoice\\";
$vName1="GHX810.out";

open(X12, "$vPath1$vName1");

while (<X12>) {
@segin = split(/\~/, $_);
# segin[3] is BIG
for ($segin[3]) {
@line = split(/\^/, $segin[3]);
$company = substr($line[4], 0, 1);
if($company == 1) {
$company = 120;
} elsif($company == 7) {
$company = 710;
} elsif($company == 8) {
$company = 800;
}
$invoice_dte = $line[1];
$invoice = $line[2];
$po_date = $line[3];
$po_number = $line[4];
$inv_typ = $line[7];
}
# segin[5] is N1 - Bill to Name
for ($segin[5]) {
@line = split(/\^/, $segin[5]);
$bt_name = $line[2];
}
# segin[6] is N3 - Bill to Address
for ($segin[6]) {
@line = split(/\^/, $segin[6]);
$bt_add1 = $line[1];
if ($line[2]) {
$bt_add2 = " ";
}else {
$bt_add2 = $line[2];
}
}
# segin[7] is N4 - Bill to City, ST Zip
for ($segin[7]) {
@line = split(/\^/, $segin[7]);
$bt_city = $line[1];
$bt_stat = $line[2];
$bt_zip = $line[3];
}
# segin[8] is N1 - SU (supplier) or BY (Purchaser)
for ($segin[8]) {
@line = split(/\^/, $segin[8]);
if ($line[1] eq "BY") {
$vendor_vname = " ";
}else {
$vendor_vname = $line[2];
}
}
# segin[9] is N1 - Ship to name
for ($segin[9]) {
@line = split(/\^/, $segin[9]);
$st_name = $line[2];
}
for ($L1 = 10; $L1 >= 220; $L1++) {
@temp = split(/\^/, $segin[$L1]);
if ($temp[0] eq "N3") {
$st_add1 = $temp[1];
if ($temp[2]) {
$st_add2 = " ";
}else {
$st_add2 = $temp[2];
}
}
elsif ($temp[0] eq "N4") {
$st_city = $temp[1];
$st_stat = $temp[2];
$st_zip = $temp[3];
}
elsif ($temp[0] eq "ITD") {
$terms = $temp[1];
$dte_code = $temp[2];
$net_days = $temp[7];
}
elsif ($temp[0] eq "DTM") {
$dtm = $segin[1];
}
elsif ($temp[0] eq "IT1") {
$line_nbr = $temp[1];
$qty = $temp[2];
$uom = $temp[3];
$price = $temp[4];
$price_cd = $temp[5];
$ven_item = $temp[7];
$item = $temp[9];
}
elsif ($temp[0] eq "PID") {
$description = $temp[5];
}
elsif ($temp[0] eq "TDS") {
$tot_inv_amt = $temp[1];
}
}
}
close(X12);
 
I saw it enter the loop with this code.. I had to make some changes to get it to run.. I took out all those goofy for's (I know they were being executed.. but they are useless overhead for what you are doing), you also need to check all of your for logic like
Code:
          if ($temp[2]) {
             $st_add2 = " ";
          }else {
             $st_add2 = $temp[2];
          }
as I explained in the other forum it doesn't make any sense unless you are expecting it to always blank out the data.

Code:
#!/usr/bin/perl



$data = 'ISA^00^          ^00^          ^01^043645501      ^01^077900207      ^090810^1019^U^00401^973397655^0^P^|~GS^IN^108878828^077900207^20090810^1019^791^X^004010~ST^810^7910004~BIG^20090807^45315897^20090807^1550510^^^DI~PER^BI^CREDIT DEPT^TE^800-426-5772~N1^BT^OCHSNER CLINIC FOUNDATION^91^00007164~N3^ACCOUNTS PAYABLE~N4^NEW ORLEANS^LA^70123~N1^BY^OCHSNER CLINIC FOUNDATION^92^7164~N1^ST^OCHSNER CLINIC NORTHSHORE^92^08978219~ITD^05^3^^20090906^^20090906^30^^^^^NET 30 DAYS~DTM^011^20090807^000000~IT1^1^2^EA^64.76^^VC^7470961~PID^F^^^^NO 9 BLACK TONER CARTRIDGE~TDS^12952~CTT^1~SE^15^7910004~GE^1^791~IEA^1^973397655~';

#### program variables

$vPath1="D:\\Invoice\\";
$vName1="GHX810.out";

#open(X12, "$vPath1$vName1");

#while (<X12>)  {
    @segin = split(/\~/, $data);
	

# segin[3] is BIG
    
          @line = split(/\^/, $segin[3]);
          $company = substr($line[4], 0, 1);
          if($company == 1) {
             $company = 120;
          } elsif($company == 7) {
             $company = 710;
          } elsif($company == 8) {
             $company = 800;
          }
          $invoice_dte = $line[1];
          $invoice     = $line[2];
          $po_date     = $line[3];
          $po_number   = $line[4];
          $inv_typ     = $line[7];

# segin[5] is N1 - Bill to Name

          @line = split(/\^/, $segin[5]);
          $bt_name = $line[2];

# segin[6] is N3 - Bill to Address
          @line = split(/\^/, $segin[6]);
          $bt_add1 = $line[1];
          if ($line[2]) {
             $bt_add2 = " ";
          }else {
             $bt_add2 = $line[2];
          }

# segin[7] is N4 - Bill to City, ST Zip

          @line = split(/\^/, $segin[7]);
          $bt_city = $line[1];
          $bt_stat = $line[2];
          $bt_zip  = $line[3];

# segin[8] is N1 - SU (supplier) or BY (Purchaser)

          @line = split(/\^/, $segin[8]);
          if ($line[1] eq "BY") {
             $vendor_vname = " ";
          }else {
             $vendor_vname = $line[2];
          }

# segin[9] is N1 - Ship to name

          @line = split(/\^/, $segin[9]);
          $st_name = $line[2];

		  
#Changed your loop to just go to the end of the array..


    for $L1 (10..$#segin) {
       @temp = split(/\^/, $segin[$L1]);
       if ($temp[0] eq "N3") {
             $st_add1 = $temp[1];
          if ($temp[2]) {
             $st_add2 = " ";
          }else {
             $st_add2 = $temp[2];
          }
       }
       elsif ($temp[0] eq "N4") {
          $st_city = $temp[1];
          $st_stat = $temp[2];
          $st_zip  = $temp[3];
       }
       elsif ($temp[0] eq "ITD") {
          $terms    = $temp[1];
          $dte_code = $temp[2];
          $net_days = $temp[7];
       }
       elsif ($temp[0] eq "DTM") {
          $dtm = $segin[1];
       }
       elsif ($temp[0] eq "IT1") {
          $line_nbr = $temp[1];
          $qty      = $temp[2];
          $uom      = $temp[3];
          $price    = $temp[4];
          $price_cd = $temp[5];
          $ven_item = $temp[7];
          $item     = $temp[9];
       }
       elsif ($temp[0] eq "PID") {
          $description = $temp[5];
       }
       elsif ($temp[0] eq "TDS") {
          $tot_inv_amt = $temp[1];
       }
    }
#}
#close(X12);

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
[noevil]
Travis - Those who say it cannot be done are usually interrupted by someone else doing it; Give the wrong symptoms, get the wrong solutions;
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top