Report Design
 Crystal Reports Forum : Crystal Reports 9 through 2020 : Report Design
Message Icon Topic: clearing array at each group Post Reply Post New Topic
Author Message
mrtj
Newbie
Newbie


Joined: 26 Mar 2013
Online Status: Offline
Posts: 26
Quote mrtj Replybullet Topic: clearing array at each group
    Posted: 29 May 2013 at 4:30am
I am trying to build an array per group built from multiple records.
I have multiple records of fields containing lets say "courses taken".
Each course itself maybe a multiple record. I mean to say someone can have "history" twice, "geography" 3 times etc .
I have tried concatenating a string, but gave up on that approach. ie.
concatenatedfield:=concatenatedfield+Table.course

So back to arrays: Each student is a group and I need to take his courses and summarize the fields onto a single line in the group footer. I am getting student 1, but student 2 contains student 1's answers and on it goes building forever to student 3. It is probably not the array that is broken, but rather the "fin" statement I use to hold the every growing string variable.
But, when I try shared stringvar fin, and clear it in the group header I get an array error.
vw is Tablename
.Student is name (yes I have real records with nothing in this field)
.Module is course (yes I have real records with nothing in this field)
build the array (note whilereadingrecords does not work correctly I get too many courses per student that are not really there's)
Lastly, I do not know the number of courses per student coming in, but I do know that 10 is and will always be the largest number they can have.
==========================
formula called out into detail section
==========================
WhilePrintingRecords;
stringvar array arrModule;
numbervar i;

if  {
vw.Module}<>"" and {vw.Student}<>""
 then
(if not({vw.Module} in arrModule) then
(
    i := i + 1;
    redim preserve arrModule;
  
      arrModule := {vw.Module};
   
));
arrModule;

==========================
formula called out in groupfooter
==========================
WhilePrintingRecords;
stringvar array arrModule;
stringvar fin;

numbervar j;
 numbervar k;
for j := 1 to ubound(arrModule) do
fin := fin + arrModule[j] + ", ";

if len(fin)> 0 then
left(fin,len(fin)-2);
=======================

Is "fin" building to infinity?
To check what is in the array, how can I print it out as is ?
in a for loop?
when I use redim arrModule[1] in a group header I get an error as this.
"A subscript must be between 1 and the size of the array"

I have seen google notes about that you cannot clear out a string variable as a shared variable when using it inside of an array????


Edited by mrtj - 29 May 2013 at 4:43am
IP IP Logged
hilfy
Admin Group
Admin Group
Avatar

Joined: 20 Nov 2006
Online Status: Offline
Posts: 3701
Quote hilfy Replybullet Posted: 29 May 2013 at 8:25am
It's not the "fin" statement, it's the fact that the array itself contains all of the values for the previous student(s).  So the second formula pulls all of that info in.
 
Try this:
 
Create a new formula.  I'll call it {@ResetArrModule}:
 
StringVar Array arrModule;
Redim arrModule[0];
 
Put this formula in the group header.  This will reset the array to a blank array at the start of each student.  So, the formula in the group footer will only have the courses for one student.
 
Another way to do this without using arrays:
 
Detail Formula:
WhilePrintingRecords;
StringVar strCourses;
If PreviousIsNull({Mytable.StudentID}) or {Mytable.StudentID} <> Previous({Mytable.StudentID}) then
strCourses := '';
If Length(strCourses) > 0 then strCourses := strCourses + ', ';
strCourses := strCourses + {MyTable.CourseDescription};
 
Group Footer:
WhilePrintingRecords;
StringVar strCourses;
strCourses
 
-Dell
 
 
IP IP Logged
mrtj
Newbie
Newbie


Joined: 26 Mar 2013
Online Status: Offline
Posts: 26
Quote mrtj Replybullet Posted: 29 May 2013 at 12:15pm
I fixed it


shared numbervar i;

if  {vw....
));
//arrModule;
i;
I changed this from not a shared variable. Then in group header set i to 0
also removed the arrModule statement that was here since I didnt need it to print in the detail part.
new footer formula
===========
WhilePrintingRecords;
stringvar array arrModule;
stringvar fin;
shared numbervar i;

numbervar j;
 numbervar k;
fin:="";             //I added this here which did help, because fin was growing even after I fixed "i"
for j := 1 to ubound(arrModule) do
fin := fin + arrModule[j] + ", ";
redim arrModule[ubound(arrModule)];

//if len(fin)> 0 then
if i >1 then left(fin,len(fin)-2);  //this fixes the fact that students with no courses were getting commas printing out .
the redim statement I added here , which index is set to be the current value of i on the current student, so when next student comes in the i could be say as high as lets say 3 courses (i=3), then I was getting 3 commas in the next non-course attending student but the left stmt above took out two of the commas leaving 1 pringing, so the if stmt took care of that saying i has to be gtr than zero.
=========
separate clear formula called out in header
===============
shared numbervar i;
 i:=0;
============
So now i is reset to zero in header, and fin is set to blanks before the for loop waddles thru the array. it works.
Now my next task is to fix the fact that the header

the reason i cannot do your string thing is I am getting 2 geographies
2 histories 3 maths etc

My final task is to sort the array alphabetically so it prints out
geogrpahy history math
and not math geography history


Edited by mrtj - 29 May 2013 at 12:18pm
IP IP Logged
hilfy
Admin Group
Admin Group
Avatar

Joined: 20 Nov 2006
Online Status: Offline
Posts: 3701
Quote hilfy Replybullet Posted: 29 May 2013 at 12:37pm
For the sort, at a sort on the course field - the sort will occur within all of the groupings.
 
For the duplicates, you could modify the string version of the formula to something like this:
 
WhilePrintingRecords;
StringVar strCourses;
If PreviousIsNull({Mytable.StudentID}) or {Mytable.StudentID} <> Previous({Mytable.StudentID}) then
strCourses := '';
If InStr(strCourses, {MyTable.CourseDescription} + ",") <= 0 then
strCourses := strCourses + {MyTable.CourseDescription} + ", ";
 
The formula for the group footer would be something like this:
 
WhilePrintingRecords;
StringVar strCourses;
Left(strCourses, Length(strCourses) - 2)
 
-Dell
IP IP Logged
mrtj
Newbie
Newbie


Joined: 26 Mar 2013
Online Status: Offline
Posts: 26
Quote mrtj Replybullet Posted: 31 May 2013 at 2:52am
I let the report dictate when a new page is inserted, I do not want to tell it to insert a new page after a footer or before a header, because the folks want it on least amount of pages as possible. So with that said when detail lines do not fit on one page, when room runs out and a page is inserted apparently the group header formulas run again, and these formulas are set to set the indexes of the array back to 1, and so I lose all the courses built up on the previous page and a student instead of having 8 courses only has his "2nd page" of detail rows accumulated.
IP IP Logged
hilfy
Admin Group
Admin Group
Avatar

Joined: 20 Nov 2006
Online Status: Offline
Posts: 3701
Quote hilfy Replybullet Posted: 31 May 2013 at 3:24am
Try changing the reset formula to something like this:
 
StringVar Array arrModule;
If not InRepeatedGroupHeader then Redim arrModule[0];
 
This should prevent it from clearing the array when the group header is repeated for a new page.
 
-Dell
IP IP Logged
mrtj
Newbie
Newbie


Joined: 26 Mar 2013
Online Status: Offline
Posts: 26
Quote mrtj Replybullet Posted: 31 May 2013 at 5:02am
that worked. thanks.

IP IP Logged
mrtj
Newbie
Newbie


Joined: 26 Mar 2013
Online Status: Offline
Posts: 26
Quote mrtj Replybullet Posted: 31 May 2013 at 5:30am
i ADDED SORT ARRAY CODE AT THE BOTTOM OF THIS LIST
//array index reset to zero for each student (group header formula)
shared numbervar i;
if not InRepeatedGroupHeader  then i:=0;
// end of group header formula

//detail section formula to group multiple records fields onto one row in footer
WhilePrintingRecords;
stringvar array arrModule;

shared numbervar i;

if  {vw.Module}<>"" and {vw.Student}<>""
 then
(if not({vw.Module} in arrModule) then
(
    i := i + 1;
    redim preserve arrModule;
  
      arrModule := {vw.Module};
   
));

i; //just printing index for debugging purposes
// end of detail formula

//formula to print collapsed courses on one row in footer and
//to do the sort . THE BIG KUHUNA
WhilePrintingRecords;
stringvar array arrModule;
stringvar fin;
shared numbervar i;
numbervar j;
stringvar temp;
booleanvar swapped := true;
//numbervar k;
// start sort
for j := 1 to ubound(arrModule) do
   while swapped = true do
   (
       swapped := false;
 
       for j := 1 to (ubound(arrModule) - 1) do (
         if arrModule[j] > arrModule[j+1] then
         (temp:=arrModule[j];
         arrModule[j]:=arrModule[j+1];
         arrModule[j+1]:=temp;
         swapped := true;
         ));
    );
        


//end sort

fin:="";
for j := 1 to ubound(arrModule) do
fin := fin + arrModule[j] + ", ";
redim arrModule[ubound(arrModule)];

//if len(fin)> 0 then
if i >1 then left(fin,len(fin)-2);
//ubound(arrModule);




IP IP Logged
Post Reply Post New Topic
Printable version Printable version

Forum Jump
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot delete your posts in this forum
You cannot edit your posts in this forum
You cannot create polls in this forum
You cannot vote in polls in this forum



This page was generated in 0.031 seconds.