From: John Darrington Date: Thu, 25 Apr 2013 10:10:36 +0000 (+0200) Subject: convert list.q to list.c X-Git-Url: https://pintos-os.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=4e5a6cc044c6c82e6c4d842bf056579b6bc47d48;p=pspp convert list.q to list.c Reviewed-by: Ben Pfaff --- diff --git a/src/language/data-io/.gitignore b/src/language/data-io/.gitignore index f6239472ba..cd4131076c 100644 --- a/src/language/data-io/.gitignore +++ b/src/language/data-io/.gitignore @@ -1,2 +1 @@ file-handle.c -list.c diff --git a/src/language/data-io/automake.mk b/src/language/data-io/automake.mk index 0695bd5d90..edb548c524 100644 --- a/src/language/data-io/automake.mk +++ b/src/language/data-io/automake.mk @@ -1,8 +1,7 @@ ## Process this file with automake to produce Makefile.in -*- makefile -*- src_language_data_io_built_sources = \ - src/language/data-io/file-handle.c \ - src/language/data-io/list.c + src/language/data-io/file-handle.c language_data_io_sources = \ src/language/data-io/combine-files.c \ @@ -19,6 +18,7 @@ language_data_io_sources = \ src/language/data-io/get.c \ src/language/data-io/inpt-pgm.c \ src/language/data-io/inpt-pgm.h \ + src/language/data-io/list.c \ src/language/data-io/placement-parser.c \ src/language/data-io/placement-parser.h \ src/language/data-io/print-space.c \ diff --git a/src/language/data-io/list.c b/src/language/data-io/list.c new file mode 100644 index 0000000000..c7f85f3917 --- /dev/null +++ b/src/language/data-io/list.c @@ -0,0 +1,266 @@ +/* PSPP - a program for statistical analysis. + Copyright (C) 1997-9, 2000, 2006, 2009-2011, 2013 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 + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . */ + +#include + +#include +#include +#include + +#include "data/casegrouper.h" +#include "data/casereader.h" +#include "data/dataset.h" +#include "data/dictionary.h" +#include "data/data-out.h" +#include "data/format.h" +#include "data/subcase.h" +#include "data/variable.h" +#include "language/command.h" +#include "language/dictionary/split-file.h" +#include "language/lexer/lexer.h" +#include "language/lexer/variable-parser.h" +#include "libpspp/compiler.h" +#include "libpspp/ll.h" +#include "libpspp/message.h" +#include "libpspp/misc.h" +#include "output/tab.h" +#include "output/table-item.h" + +#include "gl/intprops.h" +#include "gl/minmax.h" +#include "gl/xalloc.h" +#include "gl/xmalloca.h" + +#include "gettext.h" +#define _(msgid) gettext (msgid) + +enum numbering + { + format_unnumbered, + format_numbered + }; + + +struct lst_cmd +{ + int first; + int last; + int step; + struct variable **v_variables; + size_t n_variables; + enum numbering numbering; +}; + + +static int +list_execute (const struct lst_cmd *lcmd, struct dataset *ds) +{ + const struct dictionary *dict = dataset_dict (ds); + + bool ok; + int i; + struct casegrouper *grouper; + struct casereader *group; + struct subcase sc; + + subcase_init_empty (&sc); + for (i = 0; i < lcmd->n_variables; i++) + subcase_add_var (&sc, lcmd->v_variables[i], SC_ASCEND); + + + grouper = casegrouper_create_splits (proc_open (ds), dict); + while (casegrouper_get_next_group (grouper, &group)) + { + struct ccase *ccase; + struct table *t; + + ccase = casereader_peek (group, 0); + if (ccase != NULL) + { + output_split_file_values (ds, ccase); + case_unref (ccase); + } + + group = casereader_project (group, &sc); + if (lcmd->numbering == format_numbered) + group = casereader_create_arithmetic_sequence (group, 1, 1); + group = casereader_select (group, lcmd->first - 1, + (lcmd->last != LONG_MAX ? lcmd->last + : CASENUMBER_MAX), lcmd->step); + + if (lcmd->numbering == format_numbered) + { + struct fmt_spec fmt; + size_t col; + int width; + + width = lcmd->last == LONG_MAX ? 5 : intlog10 (lcmd->last); + fmt = fmt_for_output (FMT_F, width, 0); + col = caseproto_get_n_widths (casereader_get_proto (group)) - 1; + + t = table_from_casereader (group, col, _("Case Number"), &fmt); + } + else + t = NULL; + + for (i = 0; i < lcmd->n_variables; i++) + { + const struct variable *var = lcmd->v_variables[i]; + struct table *c; + + c = table_from_casereader (group, i, var_get_name (var), + var_get_print_format (var)); + t = table_hpaste (t, c); + } + + casereader_destroy (group); + + table_item_submit (table_item_create (t, "Data List")); + } + ok = casegrouper_destroy (grouper); + ok = proc_commit (ds) && ok; + + subcase_destroy (&sc); + free (lcmd->v_variables); + + return ok ? CMD_SUCCESS : CMD_CASCADING_FAILURE; +} + + +/* Parses and executes the LIST procedure. */ +int +cmd_list (struct lexer *lexer, struct dataset *ds) +{ + struct lst_cmd cmd; + const struct dictionary *dict = dataset_dict (ds); + + /* Fill in defaults. */ + cmd.step = 1; + cmd.first = 1; + cmd.last = LONG_MAX; + cmd.n_variables = 0; + cmd.v_variables = NULL; + cmd.numbering = format_unnumbered; + + + while (lex_token (lexer) != T_ENDCMD) + { + lex_match (lexer, T_SLASH); + if (lex_match_id (lexer, "VARIABLES") ) + { + lex_match (lexer, T_EQUALS); + if (! parse_variables (lexer, dict, &cmd.v_variables, &cmd.n_variables, 0 )) + { + msg (SE, _("No variables specified.")); + return CMD_FAILURE; + } + } + else if (lex_match_id (lexer, "FORMAT") ) + { + lex_match (lexer, T_EQUALS); + if (lex_match_id (lexer, "NUMBERED") ) + { + cmd.numbering = format_numbered; + } + else if (lex_match_id (lexer, "UNNUMBERED") ) + { + cmd.numbering = format_unnumbered; + } + else + { + lex_error (lexer, NULL); + goto error; + } + } + /* example: LIST /CASES=FROM 1 TO 25 BY 5. */ + else if (lex_match_id (lexer, "CASES")) + { + lex_match (lexer, T_EQUALS); + lex_force_match_id (lexer, "FROM"); + + if (lex_force_int (lexer)) + { + lex_match_int (lexer, &cmd.first); + lex_get (lexer); + } + + lex_force_match (lexer, T_TO); + + if (lex_force_int (lexer)) + { + cmd.last = lex_integer (lexer); + lex_get (lexer); + } + + lex_force_match (lexer, T_BY); + + if (lex_force_int (lexer)) + { + cmd.step = lex_integer (lexer); + lex_get (lexer); + } + } + else if (! parse_variables (lexer, dict, &cmd.v_variables, &cmd.n_variables, 0 )) + { + return CMD_FAILURE; + } + } + + + /* Verify arguments. */ + if (cmd.first > cmd.last) + { + int t; + msg (SW, _("The first case (%ld) specified precedes the last case (%ld) " + "specified. The values will be swapped."), cmd.first, cmd.last); + t = cmd.first; + cmd.first = cmd.last; + cmd.last = t; + } + + if (cmd.first < 1) + { + msg (SW, _("The first case (%ld) to list is less than 1. The value is " + "being reset to 1."), cmd.first); + cmd.first = 1; + } + + if (cmd.last < 1) + { + msg (SW, _("The last case (%ld) to list is less than 1. The value is " + "being reset to 1."), cmd.last); + cmd.last = 1; + } + + if (cmd.step < 1) + { + msg (SW, _("The step value %ld is less than 1. The value is being " + "reset to 1."), cmd.step); + cmd.step = 1; + } + + /* If no variables were explicitly provided, then default to ALL */ + if (cmd.n_variables == 0) + dict_get_vars (dict, &cmd.v_variables, &cmd.n_variables, + DC_SYSTEM | DC_SCRATCH); + + return list_execute (&cmd, ds); + + error: + free (cmd.v_variables); + return CMD_FAILURE; +} + diff --git a/src/language/data-io/list.q b/src/language/data-io/list.q deleted file mode 100644 index ddc072a46b..0000000000 --- a/src/language/data-io/list.q +++ /dev/null @@ -1,189 +0,0 @@ -/* PSPP - a program for statistical analysis. - Copyright (C) 1997-9, 2000, 2006, 2009-2011 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 - the Free Software Foundation, either version 3 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program. If not, see . */ - -#include - -#include -#include -#include - -#include "data/casegrouper.h" -#include "data/casereader.h" -#include "data/dataset.h" -#include "data/dictionary.h" -#include "data/data-out.h" -#include "data/format.h" -#include "data/subcase.h" -#include "data/variable.h" -#include "language/command.h" -#include "language/dictionary/split-file.h" -#include "language/lexer/lexer.h" -#include "libpspp/compiler.h" -#include "libpspp/ll.h" -#include "libpspp/message.h" -#include "libpspp/misc.h" -#include "output/tab.h" -#include "output/table-item.h" - -#include "gl/intprops.h" -#include "gl/minmax.h" -#include "gl/xalloc.h" -#include "gl/xmalloca.h" - -#include "gettext.h" -#define _(msgid) gettext (msgid) - -/* (headers) */ - -/* (specification) - list (lst_): - *variables=varlist("PV_NO_SCRATCH"); - cases=:from n:first,"%s>0"/by n:step,"%s>0"/ *to n:last,"%s>0"; - +format=numbering:numbered/!unnumbered, - wrap:!wrap/single. -*/ -/* (declarations) */ -/* (functions) */ - -/* Parsed command. */ -static struct cmd_list cmd; - -/* Parses and executes the LIST procedure. */ -int -cmd_list (struct lexer *lexer, struct dataset *ds) -{ - struct dictionary *dict = dataset_dict (ds); - struct casegrouper *grouper; - struct casereader *group; - struct subcase sc; - size_t i; - bool ok; - - if (!parse_list (lexer, ds, &cmd, NULL)) - return CMD_FAILURE; - - /* Fill in defaults. */ - if (cmd.step == LONG_MIN) - cmd.step = 1; - if (cmd.first == LONG_MIN) - cmd.first = 1; - if (cmd.last == LONG_MIN) - cmd.last = LONG_MAX; - if (!cmd.sbc_variables) - dict_get_vars (dict, &cmd.v_variables, &cmd.n_variables, - DC_SYSTEM | DC_SCRATCH); - if (cmd.n_variables == 0) - { - msg (SE, _("No variables specified.")); - return CMD_FAILURE; - } - - /* Verify arguments. */ - if (cmd.first > cmd.last) - { - int t; - msg (SW, _("The first case (%ld) specified precedes the last case (%ld) " - "specified. The values will be swapped."), cmd.first, cmd.last); - t = cmd.first; - cmd.first = cmd.last; - cmd.last = t; - } - if (cmd.first < 1) - { - msg (SW, _("The first case (%ld) to list is less than 1. The value is " - "being reset to 1."), cmd.first); - cmd.first = 1; - } - if (cmd.last < 1) - { - msg (SW, _("The last case (%ld) to list is less than 1. The value is " - "being reset to 1."), cmd.last); - cmd.last = 1; - } - if (cmd.step < 1) - { - msg (SW, _("The step value %ld is less than 1. The value is being " - "reset to 1."), cmd.step); - cmd.step = 1; - } - - subcase_init_empty (&sc); - for (i = 0; i < cmd.n_variables; i++) - subcase_add_var (&sc, cmd.v_variables[i], SC_ASCEND); - - grouper = casegrouper_create_splits (proc_open (ds), dict); - while (casegrouper_get_next_group (grouper, &group)) - { - struct ccase *ccase; - struct table *t; - - ccase = casereader_peek (group, 0); - if (ccase != NULL) - { - output_split_file_values (ds, ccase); - case_unref (ccase); - } - - group = casereader_project (group, &sc); - if (cmd.numbering == LST_NUMBERED) - group = casereader_create_arithmetic_sequence (group, 1, 1); - group = casereader_select (group, cmd.first - 1, - (cmd.last != LONG_MAX ? cmd.last - : CASENUMBER_MAX), cmd.step); - - if (cmd.numbering == LST_NUMBERED) - { - struct fmt_spec fmt; - size_t col; - int width; - - width = cmd.last == LONG_MAX ? 5 : intlog10 (cmd.last); - fmt = fmt_for_output (FMT_F, width, 0); - col = caseproto_get_n_widths (casereader_get_proto (group)) - 1; - - t = table_from_casereader (group, col, _("Case Number"), &fmt); - } - else - t = NULL; - - for (i = 0; i < cmd.n_variables; i++) - { - const struct variable *var = cmd.v_variables[i]; - struct table *c; - - c = table_from_casereader (group, i, var_get_name (var), - var_get_print_format (var)); - t = table_hpaste (t, c); - } - - casereader_destroy (group); - - table_item_submit (table_item_create (t, "Data List")); - } - ok = casegrouper_destroy (grouper); - ok = proc_commit (ds) && ok; - - subcase_destroy (&sc); - free (cmd.v_variables); - - return ok ? CMD_SUCCESS : CMD_CASCADING_FAILURE; -} - -/* - Local Variables: - mode: c - End: -*/