X-Git-Url: https://pintos-os.org/cgi-bin/gitweb.cgi?a=blobdiff_plain;f=src%2Fdata%2Fcasereader-translator.c;h=229dac2e54944c8df81088080c1032330c0cd84e;hb=80cc751377f06abdf4b9019dae2acce0ebfbb259;hp=523afe3fd0d9a757f5eff40c091ea372a281669d;hpb=43b1296aafe7582e7dbe6c2b6a8b478d7d9b0fcf;p=pspp diff --git a/src/data/casereader-translator.c b/src/data/casereader-translator.c index 523afe3fd0..229dac2e54 100644 --- a/src/data/casereader-translator.c +++ b/src/data/casereader-translator.c @@ -33,13 +33,12 @@ struct casereader_translator { struct casereader *subreader; /* Source of input cases. */ - void (*translate) (const struct ccase *input, struct ccase *output, - void *aux); + void (*translate) (struct ccase *input, struct ccase *output, void *aux); bool (*destroy) (void *aux); void *aux; }; -static struct casereader_class casereader_translator_class; +static const struct casereader_class casereader_translator_class; /* Creates and returns a new casereader whose cases are produced by reading from SUBREADER and passing through TRANSLATE, which @@ -56,7 +55,7 @@ static struct casereader_class casereader_translator_class; struct casereader * casereader_create_translator (struct casereader *subreader, size_t output_value_cnt, - void (*translate) (const struct ccase *input, + void (*translate) (struct ccase *input, struct ccase *output, void *aux), bool (*destroy) (void *aux), @@ -104,10 +103,65 @@ casereader_translator_destroy (struct casereader *reader UNUSED, void *ct_) } /* Casereader class for translating casereader. */ -static struct casereader_class casereader_translator_class = +static const struct casereader_class casereader_translator_class = { casereader_translator_read, casereader_translator_destroy, NULL, NULL, }; + +struct casereader_arithmetic_sequence + { + int value_ofs; + double first; + double increment; + casenumber n; + }; + +static void cas_translate (struct ccase *input, struct ccase *output, + void *aux); +static bool cas_destroy (void *aux); + +/* Creates and returns a new casereader whose cases are produced + by reading from SUBREADER and appending an additional value, + which takes the value FIRST in the first case, FIRST + + INCREMENT in the second case, FIRST + INCREMENT * 2 in the + third case, and so on. + + After this function is called, SUBREADER must not ever again + be referenced directly. It will be destroyed automatically + when the translating casereader is destroyed. */ +struct casereader * +casereader_create_arithmetic_sequence (struct casereader *subreader, + double first, double increment) +{ + /* This could be implemented with a great deal more efficiency + and generality. However, this implementation is easy. */ + struct casereader_arithmetic_sequence *cas = xmalloc (sizeof *cas); + cas->value_ofs = casereader_get_value_cnt (subreader); + cas->first = first; + cas->increment = increment; + cas->n = 0; + return casereader_create_translator (subreader, cas->value_ofs + 1, + cas_translate, cas_destroy, cas); +} + +static void +cas_translate (struct ccase *input, struct ccase *output, void *cas_) +{ + struct casereader_arithmetic_sequence *cas = cas_; + case_nullify (output); + case_move (output, input); + case_resize (output, cas->value_ofs + 1); + case_data_rw_idx (output, cas->value_ofs)->f + = cas->first + cas->increment * cas->n++; +} + +static bool +cas_destroy (void *cas_) +{ + struct casereader_arithmetic_sequence *cas = cas_; + free (cas); + return true; +}