X-Git-Url: https://pintos-os.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=src%2Fmath%2Fcategoricals.c;h=239a3a833c6dbb61dd235b7fdaf37a340c78a057;hb=372c46a3648de939ec3224cc94ad944aa39623ae;hp=a7cf3a114624d4de3a9ea5d184a516b85a1700fa;hpb=d31b04850f78d3732d318051e05529f361f0e9a5;p=pspp diff --git a/src/math/categoricals.c b/src/math/categoricals.c index a7cf3a1146..239a3a833c 100644 --- a/src/math/categoricals.c +++ b/src/math/categoricals.c @@ -96,10 +96,10 @@ lookup_variable (const struct hmap *map, const struct variable *var, unsigned in struct interact_params { - /* A map indexed by a interaction_value */ + /* A map of cases indexed by a interaction_value */ struct hmap ivmap; - const struct interaction *iact; + struct interaction *iact; int base_subscript_short; int base_subscript_long; @@ -174,6 +174,8 @@ struct categoricals const void *aux1; void *aux2; + bool sane; + const struct payload *payload; }; @@ -251,16 +253,15 @@ categoricals_destroy (struct categoricals *cat) /* Interate over each interaction value, and unref any cases that we reffed */ HMAP_FOR_EACH (iv, struct interaction_value, node, &cat->iap[i].ivmap) { -#if 0 - if (cat->payload) - cat->payload->destroy (cat->aux1, iv->user_data); -#endif + if (cat->payload && cat->payload->destroy) + cat->payload->destroy (cat->aux1, cat->aux2, iv->user_data); case_unref (iv->ccase); } free (cat->iap[i].enc_sum); free (cat->iap[i].df_prod); hmap_destroy (&cat->iap[i].ivmap); + interaction_destroy (cat->iap[i].iact); } /* Interate over each variable and delete its value map */ @@ -295,6 +296,11 @@ lookup_case (const struct hmap *map, const struct interaction *iact, const struc return iv; } +bool +categoricals_sane (const struct categoricals *cat) +{ + return cat->sane; +} struct categoricals * categoricals_create (struct interaction *const*inter, size_t n_inter, @@ -314,6 +320,7 @@ categoricals_create (struct interaction *const*inter, size_t n_inter, cat->fctr_excl = fctr_excl; cat->payload = NULL; cat->aux2 = NULL; + cat->sane = false; cat->iap = pool_calloc (cat->pool, cat->n_iap, sizeof *cat->iap); @@ -351,7 +358,12 @@ categoricals_update (struct categoricals *cat, const struct ccase *c) { int i; struct variable_node *vn = NULL; - const double weight = cat->wv ? case_data (c, cat->wv)->f : 1.0; + double weight; + + if (NULL == cat) + return; + + weight = cat->wv ? case_data (c, cat->wv)->f : 1.0; assert (NULL == cat->reverse_variable_map_short); assert (NULL == cat->reverse_variable_map_long); @@ -446,6 +458,9 @@ categoricals_n_total (const struct categoricals *cat) size_t categoricals_df_total (const struct categoricals *cat) { + if (NULL == cat) + return 0; + return cat->df_sum; } @@ -458,7 +473,7 @@ categoricals_is_complete (const struct categoricals *cat) /* This function must be called *before* any call to categoricals_get_*_by subscript and *after* all calls to categoricals_update */ -bool +void categoricals_done (const struct categoricals *cat_) { /* Implementation Note: Whilst this function is O(n) in cat->n_cats_total, in most @@ -472,6 +487,10 @@ categoricals_done (const struct categoricals *cat_) int i; int idx_short = 0; int idx_long = 0; + + if (NULL == cat) + return; + cat->df_sum = 0; cat->n_cats_total = 0; @@ -492,7 +511,10 @@ categoricals_done (const struct categoricals *cat_) struct variable_node *vn = lookup_variable (&cat->varmap, var, hash_pointer (var, 0)); if (hmap_count (&vn->valmap) == 0) - return false; + { + cat->sane = false; + return; + } cat->iap[i].df_prod[v] = df * (hmap_count (&vn->valmap) - 1); df = cat->iap[i].df_prod[v]; @@ -532,7 +554,6 @@ categoricals_done (const struct categoricals *cat_) HMAP_FOR_EACH (ivn, struct interaction_value, node, &iap->ivmap) { iap->reverse_interaction_value_map[x++] = ivn; - } assert (x <= iap->n_cats); @@ -579,12 +600,12 @@ categoricals_done (const struct categoricals *cat_) const double bin = categoricals_get_code_for_case (cat, x, iv->ccase); \ iap->enc_sum [x - iap->base_subscript_short] += bin * iv->cc; } - if (cat->payload && cat->payload->destroy) - cat->payload->destroy (cat->aux1, cat->aux2, iv->user_data); + if (cat->payload && cat->payload->calculate) + cat->payload->calculate (cat->aux1, cat->aux2, iv->user_data); } } - return true; + cat->sane = true; }