starting to look like it works
[pspp] / src / language / xforms / compute.c
index ca8f200d4faf6bd6d830a2f76438de517b384079..083d7d219f386f456bcfb0262e3d283ee4f702d5 100644 (file)
@@ -85,8 +85,8 @@ static struct expression *parse_rvalue (struct lexer *lexer,
                                        struct dataset *);
 
 static struct compute_trns *compute_trns_create (void);
-static trns_proc_func *get_proc_func (const struct lvalue *);
-static trns_free_func compute_trns_free;
+static bool compute_trns_free (void *compute_);
+static const struct trns_class *get_trns_class (const struct lvalue *);
 \f
 /* COMPUTE. */
 
@@ -109,7 +109,7 @@ cmd_compute (struct lexer *lexer, struct dataset *ds)
   if (compute->rvalue == NULL)
     goto fail;
 
-  add_transformation (ds, get_proc_func (lvalue), compute_trns_free, compute);
+  add_transformation (ds, get_trns_class (lvalue), compute);
 
   lvalue_finalize (lvalue, compute, dict);
 
@@ -129,6 +129,7 @@ compute_num (void *compute_, struct ccase **c, casenumber case_num)
 {
   struct compute_trns *compute = compute_;
 
+  printf ("compute\n");
   if (compute->test == NULL
       || expr_evaluate_num (compute->test, *c, case_num) == 1.0)
     {
@@ -265,7 +266,7 @@ cmd_if (struct lexer *lexer, struct dataset *ds)
   if (compute->rvalue == NULL)
     goto fail;
 
-  add_transformation (ds, get_proc_func (lvalue), compute_trns_free, compute);
+  add_transformation (ds, get_trns_class (lvalue), compute);
 
   lvalue_finalize (lvalue, compute, dict);
 
@@ -279,15 +280,35 @@ cmd_if (struct lexer *lexer, struct dataset *ds)
 \f
 /* Code common to COMPUTE and IF. */
 
-static trns_proc_func *
-get_proc_func (const struct lvalue *lvalue)
+static const struct trns_class *
+get_trns_class (const struct lvalue *lvalue)
 {
+  static const struct trns_class classes[2][2] = {
+    [false][false] = {
+      .name = "COMPUTE",
+      .execute = compute_str,
+      .destroy = compute_trns_free
+    },
+    [false][true] = {
+      .name = "COMPUTE",
+      .execute = compute_str_vec,
+      .destroy = compute_trns_free
+    },
+    [true][false] = {
+      .name = "COMPUTE",
+      .execute = compute_num,
+      .destroy = compute_trns_free
+    },
+    [true][true] = {
+      .name = "COMPUTE",
+      .execute = compute_num_vec,
+      .destroy = compute_trns_free
+    },
+  };
+
   bool is_numeric = lvalue_get_type (lvalue) == VAL_NUMERIC;
   bool is_vector = lvalue_is_vector (lvalue);
-
-  return (is_numeric
-          ? (is_vector ? compute_num_vec : compute_num)
-          : (is_vector ? compute_str_vec : compute_str));
+  return &classes[is_numeric][is_vector];
 }
 
 /* Parses and returns an rvalue expression of the same type as