CTABLES: Fix treatment of multiline titles.
[pspp] / src / language / stats / oneway.c
index 3665211a1c64aa61ee953a9603a2fafeef047ead..88a3641671bfefb3434cae074849c0b3e6c9cb44 100644 (file)
@@ -1,5 +1,6 @@
 /* PSPP - a program for statistical analysis.
-   Copyright (C) 1997-9, 2000, 2007, 2009, 2010, 2011, 2012, 2013, 2014 Free Software Foundation, Inc.
+   Copyright (C) 1997-9, 2000, 2007, 2009, 2010, 2011, 2012, 2013, 2014,
+   2020 Free Software Foundation, Inc.
 
    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
 
 /* Workspace variable for each dependent variable */
 struct per_var_ws
-{
-  struct interaction *iact;
-  struct categoricals *cat;
-  struct covariance *cov;
-  struct levene *nl;
+  {
+    struct interaction *iact;
+    struct categoricals *cat;
+    struct covariance *cov;
+    struct levene *nl;
 
-  double n;
+    double n;
 
-  double sst;
-  double sse;
-  double ssa;
+    double sst;
+    double sse;
+    double ssa;
 
-  int n_groups;
+    int n_groups;
 
-  double mse;
-};
+    double mse;
+  };
 
 /* Per category data */
 struct descriptive_data
-{
-  const struct variable *var;
-  struct moments1 *mom;
+  {
+    const struct variable *var;
+    struct moments1 *mom;
 
-  double minimum;
-  double maximum;
-};
+    double minimum;
+    double maximum;
+  };
 
 enum missing_type
   {
@@ -85,12 +86,6 @@ enum missing_type
     MISS_ANALYSIS,
   };
 
-enum statistics
-  {
-    STATS_DESCRIPTIVES = 0x0001,
-    STATS_HOMOGENEITY = 0x0002
-  };
-
 struct coeff_node
 {
   struct ll ll;
@@ -133,7 +128,8 @@ struct oneway_spec
 
   const struct variable *indep_var;
 
-  enum statistics stats;
+  bool descriptive_stats;
+  bool homogeneity_stats;
 
   enum missing_type missing_type;
   enum mv_class exclude;
@@ -191,7 +187,7 @@ static double bonferroni_pinv (double std_err, double alpha, double df, int k, c
 static double sidak_pinv (double std_err, double alpha, double df, int k, const struct moments1 *mom_i UNUSED, const struct moments1 *mom_j UNUSED)
 {
   const double m = k * (k - 1) / 2;
-  double lp = 1.0 - exp (log (1.0 - alpha) / m) ;
+  double lp = 1.0 - exp (log (1.0 - alpha) / m);
   return std_err * gsl_cdf_tdist_Pinv (1.0 - lp / 2.0, df);
 }
 
@@ -422,28 +418,19 @@ int
 cmd_oneway (struct lexer *lexer, struct dataset *ds)
 {
   const struct dictionary *dict = dataset_dict (ds);
-  struct oneway_spec oneway ;
-  oneway.n_vars = 0;
-  oneway.vars = NULL;
-  oneway.indep_var = NULL;
-  oneway.stats = 0;
-  oneway.missing_type = MISS_ANALYSIS;
-  oneway.exclude = MV_ANY;
-  oneway.wv = dict_get_weight (dict);
-  oneway.wfmt = dict_get_weight_format (dict);
-  oneway.alpha = 0.05;
-  oneway.posthoc = NULL;
-  oneway.n_posthoc = 0;
+  struct oneway_spec oneway = {
+    .missing_type = MISS_ANALYSIS,
+    .exclude = MV_ANY,
+    .wv = dict_get_weight (dict),
+    .wfmt = dict_get_weight_format (dict),
+    .alpha = 0.05,
+  };
 
   ll_init (&oneway.contrast_list);
-
-
   if (lex_match (lexer, T_SLASH))
     {
       if (!lex_force_match_id (lexer, "VARIABLES"))
-       {
-         goto error;
-       }
+        goto error;
       lex_match (lexer, T_EQUALS);
     }
 
@@ -469,16 +456,12 @@ cmd_oneway (struct lexer *lexer, struct dataset *ds)
           while (lex_token (lexer) != T_ENDCMD && lex_token (lexer) != T_SLASH)
            {
              if (lex_match_id (lexer, "DESCRIPTIVES"))
-               {
-                 oneway.stats |= STATS_DESCRIPTIVES;
-               }
+                oneway.descriptive_stats = true;
              else if (lex_match_id (lexer, "HOMOGENEITY"))
-               {
-                 oneway.stats |= STATS_HOMOGENEITY;
-               }
+                oneway.homogeneity_stats = true;
              else
                {
-                 lex_error (lexer, NULL);
+                 lex_error_expecting (lexer, "DESCRIPTIVES", "HOMOGENEITY");
                  goto error;
                }
            }
@@ -488,26 +471,22 @@ cmd_oneway (struct lexer *lexer, struct dataset *ds)
           lex_match (lexer, T_EQUALS);
           while (lex_token (lexer) != T_ENDCMD && lex_token (lexer) != T_SLASH)
            {
-             int p;
              bool method = false;
-             for (p = 0 ; p < sizeof (ph_tests) / sizeof (struct posthoc); ++p)
-               {
-                 if (lex_match_id (lexer, ph_tests[p].syntax))
-                   {
-                     oneway.n_posthoc++;
-                     oneway.posthoc = xrealloc (oneway.posthoc, sizeof (*oneway.posthoc) * oneway.n_posthoc);
-                     oneway.posthoc[oneway.n_posthoc - 1] = p;
-                     method = true;
-                     break;
-                   }
-               }
+             for (size_t p = 0; p < sizeof ph_tests / sizeof *ph_tests; ++p)
+                if (lex_match_id (lexer, ph_tests[p].syntax))
+                  {
+                    oneway.n_posthoc++;
+                    oneway.posthoc = xrealloc (oneway.posthoc, sizeof (*oneway.posthoc) * oneway.n_posthoc);
+                    oneway.posthoc[oneway.n_posthoc - 1] = p;
+                    method = true;
+                    break;
+                  }
              if (method == false)
                {
                  if (lex_match_id (lexer, "ALPHA"))
                    {
-                     if (!lex_force_match (lexer, T_LPAREN))
-                       goto error;
-                     if (! lex_force_num (lexer))
+                     if (!lex_force_match (lexer, T_LPAREN)
+                          || !lex_force_num (lexer))
                        goto error;
                      oneway.alpha = lex_number (lexer);
                      lex_get (lexer);
@@ -516,8 +495,7 @@ cmd_oneway (struct lexer *lexer, struct dataset *ds)
                    }
                  else
                    {
-                     msg (SE, _("The post hoc analysis method %s is not supported."), lex_tokcstr (lexer));
-                     lex_error (lexer, NULL);
+                     lex_error (lexer, _("Unknown post hoc analysis method."));
                      goto error;
                    }
                }
@@ -525,7 +503,7 @@ cmd_oneway (struct lexer *lexer, struct dataset *ds)
        }
       else if (lex_match_id (lexer, "CONTRAST"))
        {
-         struct contrasts_node *cl = xzalloc (sizeof *cl);
+         struct contrasts_node *cl = XZALLOC (struct contrasts_node);
 
          struct ll_list *coefficient_list = &cl->coefficient_list;
           lex_match (lexer, T_EQUALS);
@@ -534,20 +512,17 @@ cmd_oneway (struct lexer *lexer, struct dataset *ds)
 
           while (lex_token (lexer) != T_ENDCMD && lex_token (lexer) != T_SLASH)
            {
-             if (lex_is_number (lexer))
-               {
-                 struct coeff_node *cc = xmalloc (sizeof *cc);
-                 cc->coeff = lex_number (lexer);
-
-                 ll_push_tail (coefficient_list, &cc->ll);
-                 lex_get (lexer);
-               }
-             else
+              if (!lex_force_num (lexer))
                {
                  destroy_coeff_list (cl);
-                 lex_error (lexer, NULL);
                  goto error;
                }
+
+              struct coeff_node *cc = xmalloc (sizeof *cc);
+              cc->coeff = lex_number (lexer);
+
+              ll_push_tail (coefficient_list, &cc->ll);
+              lex_get (lexer);
            }
 
          if (ll_count (coefficient_list) <= 0)
@@ -564,47 +539,35 @@ cmd_oneway (struct lexer *lexer, struct dataset *ds)
           while (lex_token (lexer) != T_ENDCMD && lex_token (lexer) != T_SLASH)
             {
              if (lex_match_id (lexer, "INCLUDE"))
-               {
-                 oneway.exclude = MV_SYSTEM;
-               }
+                oneway.exclude = MV_SYSTEM;
              else if (lex_match_id (lexer, "EXCLUDE"))
-               {
-                 oneway.exclude = MV_ANY;
-               }
+                oneway.exclude = MV_ANY;
              else if (lex_match_id (lexer, "LISTWISE"))
-               {
-                 oneway.missing_type = MISS_LISTWISE;
-               }
+                oneway.missing_type = MISS_LISTWISE;
              else if (lex_match_id (lexer, "ANALYSIS"))
-               {
-                 oneway.missing_type = MISS_ANALYSIS;
-               }
+                oneway.missing_type = MISS_ANALYSIS;
              else
                {
-                  lex_error (lexer, NULL);
+                  lex_error_expecting (lexer, "INCLUDE", "EXCLUDE",
+                                       "LISTWISE", "ANALYSIS");
                  goto error;
                }
            }
        }
       else
        {
-         lex_error (lexer, NULL);
+         lex_error_expecting (lexer, "STATISTICS", "POSTHOC", "CONTRAST",
+                               "MISSING");
          goto error;
        }
     }
 
-
-  {
-    struct casegrouper *grouper;
-    struct casereader *group;
-    bool ok;
-
-    grouper = casegrouper_create_splits (proc_open (ds), dict);
-    while (casegrouper_get_next_group (grouper, &group))
-      run_oneway (&oneway, group, ds);
-    ok = casegrouper_destroy (grouper);
-    ok = proc_commit (ds) && ok;
-  }
+  struct casegrouper *grouper = casegrouper_create_splits (proc_open (ds), dict);
+  struct casereader *group;
+  while (casegrouper_get_next_group (grouper, &group))
+    run_oneway (&oneway, group, ds);
+  bool ok = casegrouper_destroy (grouper);
+  ok = proc_commit (ds) && ok;
 
   oneway_cleanup (&oneway);
   free (oneway.vars);
@@ -615,11 +578,7 @@ cmd_oneway (struct lexer *lexer, struct dataset *ds)
   free (oneway.vars);
   return CMD_FAILURE;
 }
-
-
 \f
-
-
 static struct descriptive_data *
 dd_create (const struct variable *var)
 {
@@ -695,33 +654,25 @@ updateit (const void *aux1, void *aux2, void *user_data,
 }
 
 static void
-run_oneway (const struct oneway_spec *cmd,
-            struct casereader *input,
+run_oneway (const struct oneway_spec *cmd, struct casereader *input,
             const struct dataset *ds)
 {
-  int v;
-  struct taint *taint;
   struct dictionary *dict = dataset_dict (ds);
-  struct casereader *reader;
-  struct ccase *c;
-
-  struct oneway_workspace ws;
-
-  ws.actual_number_of_groups = 0;
-  ws.vws = xzalloc (cmd->n_vars * sizeof (*ws.vws));
-  ws.dd_total = xmalloc (sizeof (struct descriptive_data) * cmd->n_vars);
+  struct oneway_workspace ws = {
+    .vws = xcalloc (cmd->n_vars, sizeof *ws.vws),
+    .dd_total = XCALLOC (cmd->n_vars, struct descriptive_data *),
+  };
 
-  for (v = 0 ; v < cmd->n_vars; ++v)
+  for (size_t v = 0; v < cmd->n_vars; ++v)
     ws.dd_total[v] = dd_create (cmd->vars[v]);
 
-  for (v = 0; v < cmd->n_vars; ++v)
+  for (size_t v = 0; v < cmd->n_vars; ++v)
     {
       static const struct payload payload =
         {
           .create = makeit,
           .update = updateit,
-          .calculate = NULL,
-          .destroy = killit
+          .destroy = killit,
         };
 
       ws.vws[v].iact = interaction_create (cmd->indep_var);
@@ -739,17 +690,9 @@ run_oneway (const struct oneway_spec *cmd,
       ws.vws[v].nl = levene_create (var_get_width (cmd->indep_var), NULL);
     }
 
-  c = casereader_peek (input, 0);
-  if (c == NULL)
-    {
-      casereader_destroy (input);
-      goto finish;
-    }
-  output_split_file_values (ds, c);
-  case_unref (c);
-
-  taint = taint_clone (casereader_get_taint (input));
+  output_split_file_values_peek (ds, input);
 
+  struct taint *taint = taint_clone (casereader_get_taint (input));
   input = casereader_create_filter_missing (input, &cmd->indep_var, 1,
                                             cmd->exclude, NULL, NULL);
   if (cmd->missing_type == MISS_LISTWISE)
@@ -757,13 +700,13 @@ run_oneway (const struct oneway_spec *cmd,
                                               cmd->exclude, NULL, NULL);
   input = casereader_create_filter_weight (input, dict, NULL, NULL);
 
-  reader = casereader_clone (input);
+  struct casereader *reader = casereader_clone (input);
+  struct ccase *c;
   for (; (c = casereader_read (reader)) != NULL; case_unref (c))
     {
-      int i;
       double w = dict_get_case_weight (dict, c, NULL);
 
-      for (i = 0; i < cmd->n_vars; ++i)
+      for (size_t i = 0; i < cmd->n_vars; ++i)
        {
          struct per_var_ws *pvw = &ws.vws[i];
          const struct variable *v = cmd->vars[i];
@@ -771,7 +714,7 @@ run_oneway (const struct oneway_spec *cmd,
 
          if (MISS_ANALYSIS == cmd->missing_type)
            {
-             if (var_is_value_missing (v, val, cmd->exclude))
+             if (var_is_value_missing (v, val) & cmd->exclude)
                continue;
            }
 
@@ -784,9 +727,8 @@ run_oneway (const struct oneway_spec *cmd,
   reader = casereader_clone (input);
   for (; (c = casereader_read (reader)); case_unref (c))
     {
-      int i;
       double w = dict_get_case_weight (dict, c, NULL);
-      for (i = 0; i < cmd->n_vars; ++i)
+      for (size_t i = 0; i < cmd->n_vars; ++i)
        {
          struct per_var_ws *pvw = &ws.vws[i];
          const struct variable *v = cmd->vars[i];
@@ -794,7 +736,7 @@ run_oneway (const struct oneway_spec *cmd,
 
          if (MISS_ANALYSIS == cmd->missing_type)
            {
-             if (var_is_value_missing (v, val, cmd->exclude))
+             if (var_is_value_missing (v, val) & cmd->exclude)
                continue;
            }
 
@@ -807,10 +749,9 @@ run_oneway (const struct oneway_spec *cmd,
   reader = casereader_clone (input);
   for (; (c = casereader_read (reader)); case_unref (c))
     {
-      int i;
       double w = dict_get_case_weight (dict, c, NULL);
 
-      for (i = 0; i < cmd->n_vars; ++i)
+      for (size_t i = 0; i < cmd->n_vars; ++i)
        {
          struct per_var_ws *pvw = &ws.vws[i];
          const struct variable *v = cmd->vars[i];
@@ -818,7 +759,7 @@ run_oneway (const struct oneway_spec *cmd,
 
          if (MISS_ANALYSIS == cmd->missing_type)
            {
-             if (var_is_value_missing (v, val, cmd->exclude))
+             if (var_is_value_missing (v, val) & cmd->exclude)
                continue;
            }
 
@@ -827,26 +768,22 @@ run_oneway (const struct oneway_spec *cmd,
     }
   casereader_destroy (reader);
 
-
-  for (v = 0; v < cmd->n_vars; ++v)
+  for (size_t v = 0; v < cmd->n_vars; ++v)
     {
-      const gsl_matrix *ucm;
-      gsl_matrix *cm;
       struct per_var_ws *pvw = &ws.vws[v];
-      const struct categoricals *cats = covariance_get_categoricals (pvw->cov);
-      const bool ok = categoricals_sane (cats);
 
-      if (! ok)
+      const struct categoricals *cats = covariance_get_categoricals (pvw->cov);
+      if (!categoricals_sane (cats))
        {
-         msg (MW,
-              _("Dependent variable %s has no non-missing values.  No analysis for this variable will be done."),
+         msg (MW, _("Dependent variable %s has no non-missing values.  "
+                     "No analysis for this variable will be done."),
               var_get_name (cmd->vars[v]));
          continue;
        }
 
-      ucm = covariance_calculate_unnormalized (pvw->cov);
+      const gsl_matrix *ucm = covariance_calculate_unnormalized (pvw->cov);
 
-      cm = gsl_matrix_alloc (ucm->size1, ucm->size2);
+      gsl_matrix *cm = gsl_matrix_alloc (ucm->size1, ucm->size2);
       gsl_matrix_memcpy (cm, ucm);
 
       moments1_calculate (ws.dd_total[v]->mom, &pvw->n, NULL, NULL, NULL, NULL);
@@ -865,19 +802,15 @@ run_oneway (const struct oneway_spec *cmd,
       pvw->mse = (pvw->sst - pvw->ssa) / (pvw->n - pvw->n_groups);
     }
 
-  for (v = 0; v < cmd->n_vars; ++v)
+  for (size_t v = 0; v < cmd->n_vars; ++v)
     {
       const struct categoricals *cats = covariance_get_categoricals (ws.vws[v].cov);
-
-      if (! categoricals_is_complete (cats))
-       {
-         continue;
-       }
-
-      if (categoricals_n_total (cats) > ws.actual_number_of_groups)
-       ws.actual_number_of_groups = categoricals_n_total (cats);
+      if (categoricals_is_complete (cats))
+        {
+          if (categoricals_n_total (cats) > ws.actual_number_of_groups)
+            ws.actual_number_of_groups = categoricals_n_total (cats);
+        }
     }
-
   casereader_destroy (input);
 
   if (!taint_has_tainted_successor (taint))
@@ -885,9 +818,7 @@ run_oneway (const struct oneway_spec *cmd,
 
   taint_destroy (taint);
 
- finish:
-
-  for (v = 0; v < cmd->n_vars; ++v)
+  for (size_t v = 0; v < cmd->n_vars; ++v)
     {
       covariance_destroy (ws.vws[v].cov);
       levene_destroy (ws.vws[v].nl);
@@ -899,14 +830,14 @@ run_oneway (const struct oneway_spec *cmd,
   free (ws.dd_total);
 }
 
-static void show_contrast_coeffs (const struct oneway_spec *cmd, const struct oneway_workspace *ws);
-static void show_contrast_tests (const struct oneway_spec *cmd, const struct oneway_workspace *ws);
-static void show_comparisons (const struct oneway_spec *cmd, const struct oneway_workspace *ws, int depvar);
+static void show_contrast_coeffs (const struct oneway_spec *, const struct oneway_workspace *);
+static void show_contrast_tests (const struct oneway_spec *, const struct oneway_workspace *);
+static void show_comparisons (const struct oneway_spec *, const struct oneway_workspace *, int depvar);
 
 static void
 output_oneway (const struct oneway_spec *cmd, struct oneway_workspace *ws)
 {
-  size_t i = 0;
+  size_t list_idx = 0;
 
   /* Check the sanity of the given contrast values */
   struct contrasts_node *coeff_list  = NULL;
@@ -916,13 +847,13 @@ output_oneway (const struct oneway_spec *cmd, struct oneway_workspace *ws)
       struct coeff_node *cn = NULL;
       double sum = 0;
       struct ll_list *cl = &coeff_list->coefficient_list;
-      ++i;
+      ++list_idx;
 
       if (ll_count (cl) != ws->actual_number_of_groups)
        {
          msg (SW,
               _("In contrast list %zu, the number of coefficients (%zu) does not equal the number of groups (%d). This contrast list will be ignored."),
-              i, ll_count (cl), ws->actual_number_of_groups);
+              list_idx, ll_count (cl), ws->actual_number_of_groups);
 
          ll_remove (&coeff_list->ll);
          destroy_coeff_list (coeff_list);
@@ -933,13 +864,14 @@ output_oneway (const struct oneway_spec *cmd, struct oneway_workspace *ws)
        sum += cn->coeff;
 
       if (sum != 0.0)
-       msg (SW, _("Coefficients for contrast %zu do not total zero"), i);
+       msg (SW, _("Coefficients for contrast %zu do not total zero"),
+             list_idx);
     }
 
-  if (cmd->stats & STATS_DESCRIPTIVES)
+  if (cmd->descriptive_stats)
     show_descriptives (cmd, ws);
 
-  if (cmd->stats & STATS_HOMOGENEITY)
+  if (cmd->homogeneity_stats)
     show_homogeneity (cmd, ws);
 
   show_anova_table (cmd, ws);
@@ -951,16 +883,13 @@ output_oneway (const struct oneway_spec *cmd, struct oneway_workspace *ws)
     }
 
   if (cmd->posthoc)
-    {
-      int v;
-      for (v = 0 ; v < cmd->n_vars; ++v)
-       {
-         const struct categoricals *cats = covariance_get_categoricals (ws->vws[v].cov);
+    for (size_t v = 0; v < cmd->n_vars; ++v)
+      {
+        const struct categoricals *cats = covariance_get_categoricals (ws->vws[v].cov);
 
-         if (categoricals_is_complete (cats))
-           show_comparisons (cmd, ws, v);
-       }
-    }
+        if (categoricals_is_complete (cats))
+          show_comparisons (cmd, ws, v);
+      }
 }
 
 
@@ -997,7 +926,7 @@ show_anova_table (const struct oneway_spec *cmd, const struct oneway_workspace *
       double df1 = pvw->n_groups - 1;
       double df2 = n - pvw->n_groups;
       double msa = pvw->ssa / df1;
-      double F = msa / pvw->mse ;
+      double F = msa / pvw->mse;
 
       struct entry
         {
@@ -1093,7 +1022,7 @@ show_descriptives (const struct oneway_spec *cmd, const struct oneway_workspace
          moments1_calculate (dd->mom, &n, &mean, &variance, NULL, NULL);
 
          double std_dev = sqrt (variance);
-         double std_error = std_dev / sqrt (n) ;
+         double std_error = std_dev / sqrt (n);
          double T = gsl_cdf_tdist_Qinv (q, n - 1);
 
           double entries[] = {
@@ -1118,7 +1047,7 @@ show_descriptives (const struct oneway_spec *cmd, const struct oneway_workspace
                               NULL, NULL);
 
           double std_dev = sqrt (variance);
-          double std_error = std_dev / sqrt (n) ;
+          double std_error = std_dev / sqrt (n);
           double T = gsl_cdf_tdist_Qinv (q, n - 1);
 
           double entries[] = {
@@ -1316,11 +1245,9 @@ show_contrast_tests (const struct oneway_spec *cmd, const struct oneway_workspac
          df_numerator = pow2 (df_numerator);
 
          double std_error_contrast = sqrt (pvw->mse * coef_msq);
-         double T = fabs (contrast_value / std_error_contrast);
+         double T = contrast_value / std_error_contrast;
          double T_ne = contrast_value / sec_vneq;
          double df_ne = df_numerator / df_denominator;
-          double p_ne = gsl_cdf_tdist_P (T_ne, df_ne);
-          double q_ne = gsl_cdf_tdist_Q (T_ne, df_ne);
 
           struct entry
             {
@@ -1335,13 +1262,13 @@ show_contrast_tests (const struct oneway_spec *cmd, const struct oneway_workspac
               { 1, 0, std_error_contrast },
               { 2, 0, T },
               { 3, 0, df },
-              { 4, 0, 2 * gsl_cdf_tdist_Q (T, df) },
+              { 4, 0, 2 * gsl_cdf_tdist_Q (fabs(T), df) },
               /* Do not assume equal. */
               { 0, 1, contrast_value },
               { 1, 1, sec_vneq },
               { 2, 1, T_ne },
               { 3, 1, df_ne },
-              { 4, 1, 2 * (T > 0 ? q_ne : p_ne) },
+              { 4, 1, 2 * gsl_cdf_tdist_Q (fabs(T_ne), df_ne) },
             };
 
           for (size_t i = 0; i < sizeof entries / sizeof *entries; i++)
@@ -1367,7 +1294,6 @@ show_comparisons (const struct oneway_spec *cmd, const struct oneway_workspace *
                                         _("Multiple Comparisons (%s)"),
                                         var_to_string (cmd->vars[v]))),
     "Multiple Comparisons");
-  table->omit_empty = true;
 
   struct pivot_dimension *statistics = pivot_dimension_create (
     table, PIVOT_AXIS_COLUMN, N_("Statistics"),
@@ -1412,14 +1338,14 @@ show_comparisons (const struct oneway_spec *cmd, const struct oneway_workspace *
       int test_idx = pivot_category_create_leaf (
         test->root, pivot_value_new_text (ph->label));
 
-      for (int i = 0; i < pvw->n_groups ; ++i)
+      for (int i = 0; i < pvw->n_groups; ++i)
        {
          struct descriptive_data *dd_i
             = categoricals_get_user_data_by_category (cat, i);
          double weight_i, mean_i, var_i;
          moments1_calculate (dd_i->mom, &weight_i, &mean_i, &var_i, 0, 0);
 
-         for (int j = 0 ; j < pvw->n_groups; ++j)
+         for (int j = 0; j < pvw->n_groups; ++j)
            {
              if (j == i)
                continue;