Yuri Chornoivan contributed some typo fixes
[pspp] / src / language / stats / factor.c
index f9156b7de059e597c1e77f12e300d16b5c44e716..1e369f99116087a815fa1d79de329474ee10cf32 100644 (file)
@@ -250,7 +250,7 @@ struct idata
 static struct idata *
 idata_alloc (size_t n_vars)
 {
-  struct idata *id = xzalloc (sizeof (*id));
+  struct idata *id = XZALLOC (struct idata);
 
   id->n_extractions = 0;
   id->msr = gsl_vector_alloc (n_vars);
@@ -443,7 +443,7 @@ n_extracted_factors (const struct cmd_factor *factor, struct idata *idata)
 
 
 /* Returns a newly allocated matrix identical to M.
-   It it the callers responsibility to free the returned value.
+   It is the callers responsibility to free the returned value.
 */
 static gsl_matrix *
 matrix_dup (const gsl_matrix *m)
@@ -1145,8 +1145,9 @@ cmd_factor (struct lexer *lexer, struct dataset *ds)
       if (! lex_force_match (lexer, T_RPAREN))
        goto error;
 
-      mr = create_matrix_reader_from_case_reader (dict, matrix_reader,
-                                                 &factor.vars, &factor.n_vars);
+      mr = matrix_reader_create (dict, matrix_reader);
+      factor.vars = xmemdup (mr->cvars, mr->n_cvars * sizeof *mr->cvars);
+      factor.n_vars = mr->n_cvars;
     }
   else
     {
@@ -1177,6 +1178,13 @@ cmd_factor (struct lexer *lexer, struct dataset *ds)
           free (factor.vars);
           factor.vars = vars;
           factor.n_vars = n_vars;
+
+          if (mr)
+            {
+              free (mr->cvars);
+              mr->cvars = xmemdup (vars, n_vars * sizeof *vars);
+              mr->n_cvars = n_vars;
+            }
         }
       else if (lex_match_id (lexer, "PLOT"))
        {
@@ -1314,7 +1322,7 @@ cmd_factor (struct lexer *lexer, struct dataset *ds)
              else if (lex_match_id (lexer, "ITERATE"))
                {
                  if (lex_force_match (lexer, T_LPAREN)
-                       && lex_force_int (lexer))
+                      && lex_force_int_range (lexer, "ITERATE", 0, INT_MAX))
                    {
                      n_iterations = lex_integer (lexer);
                      lex_get (lexer);
@@ -1527,8 +1535,7 @@ cmd_factor (struct lexer *lexer, struct dataset *ds)
     {
       struct idata *id = idata_alloc (factor.n_vars);
 
-      while (next_matrix_from_reader (&id->mm, mr,
-                                     factor.vars, factor.n_vars))
+      while (matrix_reader_next (&id->mm, mr, NULL))
        {
          do_factor_by_matrix (&factor, id);
 
@@ -1536,10 +1543,8 @@ cmd_factor (struct lexer *lexer, struct dataset *ds)
           id->ai_cov = NULL;
           gsl_matrix_free (id->ai_cor);
           id->ai_cor = NULL;
-         gsl_matrix_free (id->mm.corr);
-         id->mm.corr = NULL;
-         gsl_matrix_free (id->mm.cov);
-         id->mm.cov = NULL;
+
+          matrix_material_uninit (&id->mm);
        }
 
       idata_free (id);
@@ -1548,13 +1553,12 @@ cmd_factor (struct lexer *lexer, struct dataset *ds)
     if (! run_factor (ds, &factor))
       goto error;
 
-
-  destroy_matrix_reader (mr);
+  matrix_reader_destroy (mr);
   free (factor.vars);
   return CMD_SUCCESS;
 
  error:
-  destroy_matrix_reader (mr);
+  matrix_reader_destroy (mr);
   free (factor.vars);
   return CMD_FAILURE;
 }
@@ -2007,9 +2011,10 @@ do_factor (const struct cmd_factor *factor, struct casereader *r)
 static void
 do_factor_by_matrix (const struct cmd_factor *factor, struct idata *idata)
 {
-  if (!idata->mm.cov && !idata->mm.corr)
+  if (!idata->mm.cov && !(idata->mm.corr && idata->mm.var_matrix))
     {
-      msg (ME, _("The dataset has no complete covariance or correlation matrix."));
+      msg (ME, _("The dataset has no covariance matrix or a "
+                 "correlation matrix along with standard deviations."));
       return;
     }
 
@@ -2057,7 +2062,8 @@ do_factor_by_matrix (const struct cmd_factor *factor, struct idata *idata)
       gsl_matrix_free (tmp);
     }
 
-  if (factor->print & PRINT_UNIVARIATE)
+  if (factor->print & PRINT_UNIVARIATE
+      && idata->mm.n && idata->mm.mean_matrix && idata->mm.var_matrix)
     {
       struct pivot_table *table = pivot_table_create (
         N_("Descriptive Statistics"));
@@ -2091,7 +2097,7 @@ do_factor_by_matrix (const struct cmd_factor *factor, struct idata *idata)
       pivot_table_submit (table);
     }
 
-  if (factor->print & PRINT_KMO)
+  if (factor->print & PRINT_KMO && idata->mm.n)
     {
       struct pivot_table *table = pivot_table_create (
         N_("KMO and Bartlett's Test"));