struct casereader_translator
{
struct casereader *subreader; /* Source of input cases. */
-
- struct ccase *(*translate) (struct ccase *input, void *aux);
- bool (*destroy) (void *aux);
+ const struct casereader_translator_class *class;
void *aux;
};
struct casereader *
casereader_create_translator (struct casereader *subreader,
const struct caseproto *output_proto,
- struct ccase *(*translate) (struct ccase *input,
- void *aux),
- bool (*destroy) (void *aux),
+ const struct casereader_translator_class *class,
void *aux)
{
struct casereader_translator *ct = xmalloc (sizeof *ct);
- struct casereader *reader;
- ct->subreader = casereader_rename (subreader);
- ct->translate = translate;
- ct->destroy = destroy;
- ct->aux = aux;
- reader = casereader_create_sequential (
+ *ct = (struct casereader_translator) {
+ .subreader = casereader_rename (subreader),
+ .class = class,
+ .aux = aux,
+ };
+
+ struct casereader *reader = casereader_create_sequential (
NULL, output_proto, casereader_get_n_cases (ct->subreader),
&casereader_translator_class, ct);
taint_propagate (casereader_get_taint (ct->subreader),
struct casereader_translator *ct = ct_;
struct ccase *tmp = casereader_read (ct->subreader);
if (tmp)
- tmp = ct->translate (tmp, ct->aux);
+ tmp = ct->class->translate (tmp, ct->aux);
return tmp;
}
{
struct casereader_translator *ct = ct_;
casereader_destroy (ct->subreader);
- ct->destroy (ct->aux);
+ ct->class->destroy (ct->aux);
free (ct);
}
struct casereader *subreader; /* Source of input cases. */
casenumber case_offset;
- struct ccase *(*translate) (struct ccase *input, casenumber,
- const void *aux);
- bool (*destroy) (void *aux);
+ const struct casereader_translator_class *class;
void *aux;
};
cases may be skipped and never retrieved at all. If TRANSLATE is stateful,
use casereader_create_translator instead.
- The casenumber argument to the TRANSLATE function is the absolute case
- number in SUBREADER, that is, 0 when the first case in SUBREADER is being
- translated, 1 when the second case is being translated, and so on.
-
The cases returned by TRANSLATE must match OUTPUT_PROTO.
When the stateless translating casereader is destroyed, DESTROY will be
casereader_translate_stateless (
struct casereader *subreader,
const struct caseproto *output_proto,
- struct ccase *(*translate) (struct ccase *input, casenumber,
- const void *aux),
- bool (*destroy) (void *aux),
+ const struct casereader_translator_class *class,
void *aux)
{
struct casereader_stateless_translator *cst = xmalloc (sizeof *cst);
- struct casereader *reader;
- cst->subreader = casereader_rename (subreader);
- cst->translate = translate;
- cst->destroy = destroy;
- cst->aux = aux;
- reader = casereader_create_random (
+ *cst = (struct casereader_stateless_translator) {
+ .subreader = casereader_rename (subreader),
+ .class = class,
+ .aux = aux,
+ };
+ struct casereader *reader = casereader_create_random (
output_proto, casereader_get_n_cases (cst->subreader),
&casereader_stateless_translator_class, cst);
taint_propagate (casereader_get_taint (cst->subreader),
struct casereader_stateless_translator *cst = cst_;
struct ccase *tmp = casereader_peek (cst->subreader, idx);
if (tmp != NULL)
- tmp = cst->translate (tmp, cst->case_offset + idx, cst->aux);
+ tmp = cst->class->translate (tmp, cst->aux);
return tmp;
}
{
struct casereader_stateless_translator *cst = cst_;
casereader_destroy (cst->subreader);
- cst->destroy (cst->aux);
+ cst->class->destroy (cst->aux);
free (cst);
}
can->aux = aux;
can->func = func;
can->destroy = destroy;
- return casereader_create_translator (subreader, can->proto,
- can_translate, can_destroy, can);
+
+ static const struct casereader_translator_class class = {
+ can_translate, can_destroy,
+ };
+ return casereader_create_translator (subreader, can->proto, &class, can);
}
car->err = err;
car->prev_value = SYSMIS;
- return casereader_create_translator (subreader, car->proto,
- car_translate, car_destroy, car);
+ static const struct casereader_translator_class class = {
+ car_translate, car_destroy
+ };
+ return casereader_create_translator (subreader, car->proto, &class, car);
}
const struct variable *weight)
{
struct casereader *u ;
- struct casereader *ud ;
struct caseproto *output_proto = caseproto_ref (casereader_get_proto (input));
struct consolidator *cdr = xmalloc (sizeof (*cdr));
u = casereader_create_filter_func (input, uniquify,
NULL, cdr, NULL);
- ud = casereader_create_translator (u,
- output_proto,
- consolodate_weight,
- uniquify_destroy,
- cdr);
-
- return ud;
+ static const struct casereader_translator_class class = {
+ consolodate_weight, uniquify_destroy,
+ };
+ return casereader_create_translator (u, output_proto, &class, cdr);
}
casereader_create_counter (struct casereader *, casenumber *counter,
casenumber initial_value);
+struct casereader_translator_class
+ {
+ struct ccase *(*translate) (struct ccase *, void *aux);
+ bool (*destroy) (void *aux);
+ };
struct casereader *
casereader_create_translator (struct casereader *,
const struct caseproto *output_proto,
- struct ccase *(*translate) (struct ccase *,
- void *aux),
- bool (*destroy) (void *aux),
+ const struct casereader_translator_class *,
void *aux);
-
struct casereader *
casereader_translate_stateless (struct casereader *,
const struct caseproto *output_proto,
- struct ccase *(*translate) (struct ccase *,
- casenumber idx,
- const void *aux),
- bool (*destroy) (void *aux),
+ const struct casereader_translator_class *,
void *aux);
struct casereader *casereader_project (struct casereader *,