Okay, this is really obnoxious. I will put a commentary after it.
// Note: throughout this each part of a record, like a line, will be referred to as a 'subrecord'
// additionally parts of a subrecord are referred to as 'elements'.
// There should be a 0; at the end of each step for benefit of code readability. It isn't really part of the working code.
//Part 1; Setting up the variables
stringvar array strarrWorking1st;
stringvar array strarrWorking2nd;
local stringvar array strarrLoopArray1;
local stringvar array strarr01Event;
local stringvar array strarr02From;
local stringvar array strarr03To;
local stringvar array strarr04By;
local datetimevar array dtarr05When;
local numbervar array numarr06Howlong;
stringvar array strarrNames;
numbervar array numarrHours;
numbervar numNames;
local stringvar strWorking;
local numbervar i;
local numbervar j;
local numbervar numUpperLimit;
local numbervar numUpperLimit2;
local numbervar numCounter2:=1;
strWorking:={@data};
redim strarrLoopArray1[5]; //this sets us to five elements,
0;
//Part 2; separating the lines out.
strWorking:=Replace(strWorking, " PM ", " PM###");
strWorking:=Replace(strWorking, " AM ", " AM###");
strWorking:=Replace(strWorking, "'", " ");
strarrWorking1st:=Split(strWorking,"###",1000); //this puts each line into individual array slots
numUpperLimit:=Ubound(strarrWorking1st); //This finds the size of the array
redim strarrWorking2nd[numUpperLimit]; //This makes the second array a little smaller and clears it out.
For i := 1 To numUpperLimit Do //This starts a loop, looking through the array.
(
if instr(strarrWorking1st,"Person Assigned changed")>0 or i=numUpperLimit then //Check for the right record type
( //We will want the last element in the whole log to go in as well.
strarrWorking2nd[numCounter2]:=strarrWorking1st; //If the right record type, copy into 2nd array
numCounter2:=numCounter2+1; //increment the counter on the second array.
)
); //end loop
//At this point the second array should contain only the 'lines' we want from the original
0;
//Part 3; Making each line go into component parts, and put them into arrays.
//Next we need to separate the events into their component parts. And keep them there.
// This requires that each line be looked at, chunked into a mini array of five elements and then
// those five elements need to go into their five arrays.
redim preserve strarrWorking2nd[numCounter2-1]; //Shrings the array again, without cleaning it out.
local numbervar numUpperLimit2:=Ubound(strarrWorking2nd);
redim strarr01Event[numUpperLimit2];
redim strarr02From[numUpperLimit2];
redim strarr03To[numUpperLimit2];
redim strarr04By[numUpperLimit2];
redim dtarr05When[numUpperLimit2];
strWorking:="";
//for each element then we replace ' from ', ' to ', ' by ' and ' at '
For i := 1 To numUpperLimit2 Do (
strWorking:=strarrWorking2nd;
if i=numUpperLimit2 then //Checks to see if we are at the last element, which won't match the others in type.
(
strWorking:=Replace(strWorking, " at ", "###");
strarrLoopArray1:=split(strWorking,"###"); //breaks it into two elements if last record.
dtarr05When=cdatetime(strarrLoopArray1[2]); //loads only the last array, the date field.
strarr01Event="LAST RECORD";
); //ends last record handling.
if i<>numUpperLimit2 then //Normal subrecords follow.
(
strWorking:=Replace(strWorking, " from ", "###");
strWorking:=Replace(strWorking, " to ", "###");
strWorking:=Replace(strWorking, " by ", "###");
strWorking:=Replace(strWorking, " at ", "###");
strarrLoopArray1:=split(strWorking,"###"); //breaks it into five elements if normal subrecord
//loads each element into five arrays.
strarr01Event:=strarrLoopArray1[1];
strarr02From:=strarrLoopArray1[2];
strarr03To:=strarrLoopArray1[3];
strarr04By:=strarrLoopArray1[4];
dtarr05When:=cdatetime(strarrLoopArray1[5]);
); //ends the normal subrecord handling.
); //ends the loop
0;
//Part 4; Get the time/date difference.
// Next we can determine how long it is from one event to the next.
// We know what a given time is and where it is in the array, we know what the next element is.
// So we do a datediff on them. We have to know when the ticket ends, of course, to get the last element to come out properly.
// This gets stored in yet another arrray. Each element in this array corresponds to the
// element number we are using for each of the above arrays. All of them are in lock-step together.
redim numarr06Howlong[numUpperLimit2];
For i := 1 To numUpperLimit2-1 Do //Don't need the last element.
(
numarr06Howlong:=datediff("h",dtarr05When,dtarr05When[i+1]); //gets the datediff in hours between element and next element.
);
0;
//Part 5. Totals per person.
//Next we need to total these values up, but we have to do it per person.
// In order to do this we have two more arrays, one for each name, and one for the current total.
numNames:=distinctcount(strarr03To)+1; //This figures out how many elements we need. We need an extra for blanks.
redim strarrNames[numNames];
redim numarrHours[numNames];
numCounter2:=1;
For i:= 1 to numUpperLimit2 Do //This puts unique names into the array.
(
if strarr02From<>"" and strarr02From <> strarrNames //This checks the whole array for presence of the name.
then (strarrNames[numCounter2]:=strarr02From;
numCounter2:=numCounter2+1);
);
//For each subrecord we will find the appropriate bin and put it in.
For i := 1 To numUpperLimit2 Do
(
For j := 1 to numNames Do
(
if strarrNames[j]=strarr02From then //if the names are the same, dump it in the bin
(numarrHours[j]:=numarrHours[j]+numarr06Howlong);
)
);
0;
and to display
local numbervar j;
numbervar numNames;
stringvar array strarrNames;
numbervar array numarrHours;
local stringvar strDisplay:="";
For j := 1 to numNames Do
(
if strarrNames[j]<>"" then strDisplay:=strDisplay+strarrNames[j] +" "+totext(numarrHours[j])+chrw(13);
);
strDisplay;