[LON-CAPA-cvs] cvs: modules /matthew/spreadsheet Spreadsheet.pm assesscalc.pm classcalc.pm studentcalc.pm

matthew lon-capa-cvs@mail.lon-capa.org
Thu, 10 Apr 2003 21:12:21 -0000


This is a MIME encoded message

--matthew1050009141
Content-Type: text/plain

matthew		Thu Apr 10 17:12:21 2003 EDT

  Modified files:              
    /modules/matthew/spreadsheet	Spreadsheet.pm assesscalc.pm 
                                	classcalc.pm studentcalc.pm 
  Log:
  caching works reasonably well, as does the computation of spreadsheets.
  Much remains to be done.
  
  
--matthew1050009141
Content-Type: text/plain
Content-Disposition: attachment; filename="matthew-20030410171221.txt"

Index: modules/matthew/spreadsheet/Spreadsheet.pm
diff -u modules/matthew/spreadsheet/Spreadsheet.pm:1.1 modules/matthew/spreadsheet/Spreadsheet.pm:1.2
--- modules/matthew/spreadsheet/Spreadsheet.pm:1.1	Wed Apr  9 16:57:56 2003
+++ modules/matthew/spreadsheet/Spreadsheet.pm	Thu Apr 10 17:12:21 2003
@@ -1,5 +1,5 @@
 #
-# $Id: Spreadsheet.pm,v 1.1 2003/04/09 20:57:56 matthew Exp $
+# $Id: Spreadsheet.pm,v 1.2 2003/04/10 21:12:21 matthew Exp $
 #
 # Copyright Michigan State University Board of Trustees
 #
@@ -260,7 +260,6 @@
 #-------------------------------------------------------
 sub MEAN {
     my $mask=&mask(@_);
-#    $errorlog.='(mask = '.$mask.' )';
     my $sum=0; 
     my $num=0;
     foreach (grep /$mask/,keys(%sheet_values)) {
@@ -287,7 +286,6 @@
 #-------------------------------------------------------
 sub STDDEV {
     my $mask=&mask(@_);
-#    $errorlog.='(mask = '.$mask.' )';
     my $sum=0; my $num=0;
     foreach (grep /$mask/,keys(%sheet_values)) {
         $sum+=$sheet_values{$_};
@@ -474,17 +472,16 @@
 
 
 sub calc {
-#    $errorlog .= "\%t has ".(keys(%t))." keys\n";
-    %sheet_values = %t; # copy %t into %sheet_values.
-#    $errorlog .= "\%sheet_values has ".(keys(%sheet_values))." keys\n";
-    my $notfinished=1;
-    my $lastcalc='';
-    my $depth=0;
+    %sheet_values = %t;
+    my $notfinished = 1;
+    my $lastcalc = '';
+    my $depth = 0;
     while ($notfinished) {
 	$notfinished=0;
         while (my ($cell,$value) = each(%t)) {
             my $old=$sheet_values{$cell};
             $sheet_values{$cell}=eval $value;
+#            $errorlog .= $cell.' = '.$old.'->'.$sheet_values{$cell}."\n";
 	    if ($@) {
 		undef %sheet_values;
                 return $cell.': '.$@;
@@ -494,6 +491,8 @@
                 $lastcalc=$cell; 
             }
         }
+#        $errorlog.="------------------------------------------------";
+
         $depth++;
         if ($depth>100) {
 	    undef %sheet_values;
@@ -684,10 +683,57 @@
     }
 }
 
+sub sett {
+    my $self = shift;
+    my %t=();
+    #
+    # Deal with the template row
+    foreach my $col ($self->template_cells()) {
+        next if ($col=~/^[A-Z]/);
+        foreach my $row ($self->rows()) {
+            # Get the name of this cell
+            my $cell=$col.$row;
+            # Grab the template declaration
+            $t{$cell}=$self->formula('template_'.$col);
+            # Replace '#' with the row number
+            $t{$cell}=~s/\#/$row/g;
+            # Replace '....' with ','
+            $t{$cell}=~s/\.\.+/\,/g;
+            # Replace 'A0' with the value from 'A0'
+            $t{$cell}=~s/(^|[^\"\'])([A-Za-z]\d+)/$1\$sheet_values\{\'$2\'\}/g;
+            # Replace parameters
+            $t{$cell}=~s/(^|[^\"\'])\[([^\]]+)\]/$1.$self->expandnamed($2)/ge;
+        }
+    }
+    #
+    # Deal with the normal cells
+    while (my($cell,$formula) = each(%{$self->{'formulas'}})) {
+	next if ($_=~/template\_/);
+        my ($col,$row) = ($cell =~ /([A-z])(\d+)/);
+        if ($row eq '0') {
+            $t{$cell}=$formula;
+            $t{$cell}=~s/\.\.+/\,/g;
+            $t{$cell}=~s/(^|[^\"\'])([A-Za-z]\d+)/$1\$sheet_values\{\'$2\'\}/g;
+            $t{$cell}=~s/(^|[^\"\'])\[([^\]]+)\]/$1.$self->expandnamed($2)/ge;
+        } elsif  ( $col  =~ /^[A-Z]$/  ) {
+            if ($formula !~ /^\!/) {
+                my $data  = $self->{'constants'}->{$cell};
+                $t{$cell} = $data if (defined($data) && $data ne '');
+            }
+        } else {
+            $t{$cell}=$formula;
+            $t{$cell}=~s/\.\.+/\,/g;
+            $t{$cell}=~s/(^|[^\"\'])([A-Za-z]\d+)/$1\$sheet_values\{\'$2\'\}/g;
+            $t{$cell}=~s/(^|[^\"\'])\[([^\]]+)\]/$1.$self->expandnamed($2)/ge;
+        }
+    }
+    %{$self->{'safe'}->varglob('t')}=%t;
+}
+
 #
 # sett Set up the temporary hash used for computation
 #
-sub sett {
+sub old_sett {
     my $self = shift;
     my %t=();
     my $pattern='';
@@ -962,6 +1008,7 @@
     $self->clear_errorlog();
     $self->sett();
     my $result =  $self->{'safe'}->reval('&calc();');
+#    $self->logthis($self->get_errorlog());
     %{$self->{'values'}} = %{$self->{'safe'}->varglob('sheet_values')};
 #    $self->logthis($self->get_errorlog());
     return $result;
Index: modules/matthew/spreadsheet/assesscalc.pm
diff -u modules/matthew/spreadsheet/assesscalc.pm:1.1 modules/matthew/spreadsheet/assesscalc.pm:1.2
--- modules/matthew/spreadsheet/assesscalc.pm:1.1	Wed Apr  9 16:57:56 2003
+++ modules/matthew/spreadsheet/assesscalc.pm	Thu Apr 10 17:12:21 2003
@@ -1,5 +1,5 @@
 #
-# $Id: assesscalc.pm,v 1.1 2003/04/09 20:57:56 matthew Exp $
+# $Id: assesscalc.pm,v 1.2 2003/04/10 21:12:21 matthew Exp $
 #
 # Copyright Michigan State University Board of Trustees
 #
@@ -77,7 +77,7 @@
     %Exportrows = undef;
     my @tmp = &Apache::lonnet::dump('nohist_calculatedsheets_'.
                                     $ENV{'request.course.id'},
-                                    $sname,$sdomain);
+                                    $sdomain,$sname,undef);
     if ($tmp[0]!~/^error/) {
         my %tmp = @tmp;
         # We only got one key, so we will access it directly.
@@ -87,11 +87,18 @@
                 $Exportrows{$symb}->{'time'} = $sheetdata;
             } else {
                 $sheetdata =~ s/^___=___//;
-                $Exportrows{$symb}->{'data'} = {split('___;___',$sheetdata)};
+                my @Data = split('___;___',$sheetdata);
+                $Exportrows{$symb}->{'data'} = \@Data;
             }
         }
     }
+    foreach my $symb (keys(%Exportrows)) {
+        if (! exists($Exportrows{$symb}->{'data'}) ||
+            ! defined($Exportrows{$symb}->{'data'})) {
+            delete($Exportrows{$symb});
+        }
 
+    }
 }
 
 sub setup_parameter_caches {
@@ -189,8 +196,6 @@
     my $courselevelm = $usercourseprefix.'.'.$mapparm;
     foreach ($symbparm, $mapparm,$usercourseprefix,$seclevel,
              $seclevelr,$seclevelm,$courselevel,$courselevelr,$courselevelm) {
-#        $self->logthis('level = '.$_);
-#        $self->logthis('value = '.$courseopt{$_}) if (exists($courseopt{$_}));
     }
     # fourth, check user
     if (defined($uname)) {
@@ -360,7 +365,6 @@
 
 sub compute {
     my $self = shift;
-    $self->logthis('computing');
     $self->initialize_safe_space();
     #
     # Definitions
@@ -400,6 +404,11 @@
         $self->logthis('unable to tie '.$filename);
     }
     #
+    # Clean out unnecessary parameters
+    foreach (keys(%parameters)) {
+        delete($parameters{$_}) if (! /(resource\.|stores_|parameter_)/);
+    }
+    #
     # Get the students performance data
     my %student_parameters;
     %student_parameters = 
@@ -413,11 +422,6 @@
         $parameters{$parm} = $value;
     }
     #
-    # Clean out unnecessary parameters
-    foreach (keys(%parameters)) {
-        delete($parameters{$_}) if (! /(resource\.|stores_|parameter_)/);
-    }
-    #
     # Set up the formulas and parameter values
     my %f=$self->formulas();
     my %c;
@@ -426,7 +430,6 @@
         next if ($cell !~ /^A/ || $cell eq 'A0');
         $c{$formula}=$parameters{$formula};
         $have_seen{$formula}++;
-        $self->logthis('seen '.$formula);
     }
     while (my ($parm,$value) = each(%parameters)) {
         next if ($have_seen{$parm});
@@ -501,9 +504,14 @@
     my $symb = $self->{'symb'};
     if (! exists($Exportrows{$symb}) || ! defined($Exportrows{$symb}) ||
         ! $self->check_expiration_time($Exportrows{$symb}->{'time'})) {
+        $self->logthis('computing...');
         $self->compute();
     }
-    return @{$Exportrows{$symb}->{'data'}};
+    my @Data = @{$Exportrows{$symb}->{'data'}};
+    for (my $i=0;$i<$#Data;$i++) {
+        $Data[$i]="'".$Data[$i]."'" if ($Data[$i]=~/\D/ && defined($Data[$i]));
+    }
+    return @Data;
 }
 
 sub save_export_data {
Index: modules/matthew/spreadsheet/classcalc.pm
diff -u modules/matthew/spreadsheet/classcalc.pm:1.1 modules/matthew/spreadsheet/classcalc.pm:1.2
--- modules/matthew/spreadsheet/classcalc.pm:1.1	Wed Apr  9 16:57:56 2003
+++ modules/matthew/spreadsheet/classcalc.pm	Thu Apr 10 17:12:21 2003
@@ -1,5 +1,5 @@
 #
-# $Id: classcalc.pm,v 1.1 2003/04/09 20:57:56 matthew Exp $
+# $Id: classcalc.pm,v 1.2 2003/04/10 21:12:21 matthew Exp $
 #
 # Copyright Michigan State University Board of Trustees
 #
@@ -47,7 +47,8 @@
 
 use strict;
 use Apache::Constants qw(:common :http);
-use Apache::loncoursedata;
+use Apache::loncoursedata();
+use Apache::lonhtmlcommon();
 use Apache::Spreadsheet;
 use Apache::studentcalc;
 use HTML::Entities();
@@ -73,7 +74,8 @@
         # the wrong section, have expired or pending roles, whatever...
         push (@Students,$studenthash);
     }
-    return @Students;
+    my @SortedStudents = sort { $a->{'fullname'} cmp $b->{'fullname'} } @Students;
+    return @SortedStudents;
 }
 
 sub gettitle {
@@ -104,11 +106,11 @@
     my $label_num = 0;
     foreach (split(//,'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz')){
         if ($label_num<$num_uneditable) { 
-            $tableheader.='<td bgcolor="#FFDDDD">';
+            $tableheader.='<th bgcolor="#FFDDDD">';
         } else {
-            $tableheader.='<td>';
+            $tableheader.='<th>';
         }
-        $tableheader.="<b><font size=+1>$_</font></b></td>";
+        $tableheader.="<b><font size=+1>$_</font></b></th>";
         $label_num++;
     }
     $tableheader.="</tr>\n";
@@ -122,33 +124,34 @@
     # Print out summary/export row
     $r->print('<tr><td>Summary</td><td>0</td>'.
 	      $self->html_row($num_uneditable,0)."</tr>\n");
-    $r->print("</table>\n");
     #
     # Prepare to output rows
     $tableheader =<<"END";
 <table border="2">
-<tr><th></th>
+<tr><th>Row</th>
   <th>student</th><th>username</th><th>domain</th>
   <th>section</th><th>status</th>
 END
     foreach (split(//,'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz')){
 	if ($label_num<$num_uneditable) { 
-            $tableheader.='<td bgcolor="#FFDDDD">';
+            $tableheader.='<th bgcolor="#FFDDDD">';
         } else {
-            $tableheader.='<td>';
+            $tableheader.='<th>';
         }
-        $tableheader.="<b><font size=+1>$_</font></b></td>";
+        $tableheader.="<b><font size=+1>$_</font></b></th>";
     }
     #
-    my $num_output = 1;
+    my $num_output = 0;
     foreach my $student ($self->get_classlist()) {
 	if ($num_output++ % 50 == 0) {
 	    $r->print("</table>\n".$tableheader);
 	}
-	my $rownum = $self->get_row_number_from_key($student);
+	my $rownum = $self->get_row_number_from_key
+	    ($student->{'username'}.':'.$student->{'domain'});
+
         my $link = '<a href="/adm/studentcalc?sname='.$student->{'username'}.
             '&sdomain='.$student->{'domain'}.'">';
-	$r->print('<tr>'.
+	$r->print('<tr>'.'<td>'.$rownum.'</td>'.
 		  '<td>'.$link.$student->{'fullname'}.'</a></td>'.
 		  '<td>'.$student->{'username'}.'</td>'.
 		  '<td>'.$student->{'domain'}  .'</td>'.
@@ -178,7 +181,7 @@
 sub display {
     my $self = shift;
     my ($r) = @_;
-    $self->compute();
+    $self->compute($r);
     # display as html/csv/excel/etc....
     $self->outsheet_html($r);
     return;
@@ -186,7 +189,14 @@
 
 sub compute {
     my $self = shift;
+    my ($r) = @_;
     $self->initialize_safe_space();
+    my %c = $self->constants();
+    my %f = $self->formulas();
+    my @Students = $self->get_classlist();
+    my %prog_state=&Apache::lonhtmlcommon::Create_PrgWin
+        ($r,'Spreadsheet Computation Status',
+         'Spreadsheet Computation', scalar(@Students));
     &Apache::studentcalc::initialize_package();
     foreach my $student ($self->get_classlist()) {
 	my $studentsheet = Apache::studentcalc->new
@@ -198,9 +208,19 @@
 	# hash and array slices....
 	my $i=0;
 	foreach (split(//,'ABCDEFGHIJKLMNOPQRSTUVWXYZ')) {
-	    $self->{'constants'}->{$_.$rownum}=$exportdata[$i++];
+            my $cell = $_.$rownum;
+            my $data = $exportdata[$i];
+            $f{$cell} = $data if (defined($data));
+            $c{$cell} = $data if (defined($data));
+            $i++;
 	}
+        &Apache::lonhtmlcommon::Increment_PrgWin($r,\%prog_state,
+                                                 'last student');
     }
+    &Apache::lonhtmlcommon::Close_PrgWin($r,\%prog_state);
+    $r->rflush();
+    $self->constants(\%c);
+    $self->formulas(\%f);
     $self->calcsheet();
 }
 
Index: modules/matthew/spreadsheet/studentcalc.pm
diff -u modules/matthew/spreadsheet/studentcalc.pm:1.1 modules/matthew/spreadsheet/studentcalc.pm:1.2
--- modules/matthew/spreadsheet/studentcalc.pm:1.1	Wed Apr  9 16:57:56 2003
+++ modules/matthew/spreadsheet/studentcalc.pm	Thu Apr 10 17:12:21 2003
@@ -1,5 +1,5 @@
 #
-# $Id: studentcalc.pm,v 1.1 2003/04/09 20:57:56 matthew Exp $
+# $Id: studentcalc.pm,v 1.2 2003/04/10 21:12:21 matthew Exp $
 #
 # Copyright Michigan State University Board of Trustees
 #
@@ -78,7 +78,7 @@
     %Exportrows = undef;
     my @tmp = &Apache::lonnet::dump('nohist_calculatedsheets',
 		     $ENV{'course.'.$ENV{'request.course.id'}.'.domain'},
-				    $ENV{'request.course.id'},,undef);
+		     $ENV{'course.'.$ENV{'request.course.id'}.'.num'},undef);
     if ($tmp[0]!~/^error/) {
         my %tmp = @tmp;
         # We only got one key, so we will access it directly.
@@ -89,9 +89,12 @@
                 $Exportrows{$student}->{'time'} = $sheetdata;
             } else {
                 $sheetdata =~ s/^___=___//;
-                $Exportrows{$student}->{'data'} = {split('___;___',$sheetdata)};
+                my @Data = split('___;___',$sheetdata);
+                $Exportrows{$student}->{'data'} = \@Data;
             }
         }
+    } else {
+        &Apache::lonnet::logthis('unable to read cached student export rows');
     }
 }
 
@@ -163,7 +166,6 @@
     if (scalar(@Sequences)< 1) {
         &initialize_package();
     }
-    &Apache::lonnet::logthis('number of sequences:'.(scalar(@Sequences)));
     foreach my $Sequence (@Sequences) {
 	next if ($Sequence->{'num_assess'} < 1);
 	$r->print("<h2>".$Sequence->{'title'}."</h2>\n");
@@ -213,15 +215,14 @@
         my ($top,$sequences,$assessments) = 
             &Apache::loncoursedata::get_sequence_assessment_data();
         if (! defined($top) || ! ref($top)) {
-            # There has been an error, better report it
             &Apache::lonnet::logthis('top is undefined');
             return;
         }
         @sequences = @{$sequences} if (ref($sequences) eq 'ARRAY');
     }
-    &Apache::lonnet::logthis('num seq = '.(scalar(@sequences)));
-    &Apache::assesscalc::initialize_package($self->{'name'},
-                                            $self->{'domain'});
+    &Apache::assesscalc::initialize_package($self->{'name'},$self->{'domain'});
+    my %c = $self->constants();
+    my %f = $self->formulas();
     foreach my $seq (@sequences) {
         next if ($seq->{'num_assess'}<1);
         foreach my $resource (@{$seq->{'contents'}}) {
@@ -230,16 +231,25 @@
                 ($self->{'name'},$self->{'domain'},$resource->{'symb'});
             my @exportdata = $assessSheet->export_data();
             my $rownum = $self->get_row_number_from_key
-                ($self->{'name'}.':'.$self->{'domain'});
+                               ($resource->{'symb'});
             # I really want to try doing the following assignment using
             # hash and array slices....
             my $i=0;
             foreach (split(//,'ABCDEFGHIJKLMNOPQRSTUVWXYZ')) {
-                $self->{'constants'}->{$_.$rownum}=$exportdata[$i++];
+                my $cell = $_.$rownum;
+                my $data = $exportdata[$i];
+#                $self->logthis("setting $cell = $data");
+                $f{$cell} = $data if (defined($data));
+                $c{$cell} = $data if (defined($data));
+                $i++;
             }
         }
     }
+    $self->constants(\%c);
+    $self->formulas(\%f);
+#    $self->dump_values_to_log();
     $self->calcsheet();
+#    $self->dump_values_to_log();    
     #
     # Store export row in cache
     my @exportarray=();
@@ -278,7 +288,11 @@
         ! $self->check_expiration_time($Exportrows{$student}->{'time'})) {
         $self->compute();
     }
-    return @{$Exportrows{$student}->{'data'}};
+    my @Data = @{$Exportrows{$student}->{'data'}};
+    for (my $i=0; $i<=$#Data;$i++) {
+        $Data[$i]="'".$Data[$i]."'" if ($Data[$i]=~/\D/ && defined($Data[$i]));
+    }
+    return @Data;
 }
 
 1;

--matthew1050009141--