You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-02111-1307, USA. */
+Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301, USA. */
#include <config.h>
#include <gsl/gsl_cdf.h>
/* (specification)
"EXAMINE" (xmn_):
- *variables=custom;
+ *^variables=custom;
+total=custom;
+nototal=custom;
+missing=miss:pairwise/!listwise,
struct factor *factor);
static void show_percentiles(struct variable **dependent_var,
- int n_dep_var,
- struct factor *factor);
+ int n_dep_var,
+ struct factor *factor);
void box_plot_variables(const struct factor *fctr,
- struct variable **vars, int n_vars,
+ const struct variable **vars, int n_vars,
const struct variable *id
);
/* Represent a factor as a string, so it can be
printed in a human readable fashion */
const char * factor_to_string(const struct factor *fctr,
- struct factor_statistics *fs,
- const struct variable *var);
+ struct factor_statistics *fs,
+ const struct variable *var);
/* Represent a factor as a string, so it can be
multipass_procedure_with_splits (run_examine, &cmd);
if ( totals )
- free(totals);
+ {
+ free( totals );
+ }
+
+ if ( dependent_vars )
+ free (dependent_vars);
+
+ {
+ struct factor *f = factors ;
+ while ( f )
+ {
+ struct factor *ff = f;
+
+ f = f->next;
+ free ( ff->fs );
+ hsh_destroy ( ff->fstats ) ;
+ free ( ff ) ;
+ }
+ }
subc_list_double_destroy(&percentile_list);
}
+/* Create a hash table of percentiles and their values from the list of
+ percentiles */
static struct hsh_table *
list_to_ptile_hash(const subc_list_double *l)
{
struct percentile *p = xmalloc (sizeof (struct percentile));
p->p = subc_list_double_at(l,i);
+ p->v = SYSMIS;
hsh_insert(h, p);
lex_match('(');
- while ( lex_double_p() )
+ while ( lex_is_number() )
{
- subc_list_double_push(&percentile_list,lex_double());
+ subc_list_double_push(&percentile_list,lex_number());
lex_get();
-/* Parser for the variables sub command */
+/* Parser for the variables sub command
+ Returns 1 on success */
static int
xmn_custom_variables(struct cmd_examine *cmd )
{
-
lex_match('=');
if ((token != T_ID || dict_lookup_var (default_dict, tokid) == NULL)
&& token != T_ALL)
- return 2;
+ {
+ return 2;
+ }
if (!parse_variables (default_dict, &dependent_vars, &n_dependent_vars,
PV_NO_DUPLICATE | PV_NUMERIC | PV_NO_SCRATCH) )
if ( lex_match(T_BY))
{
- return examine_parse_independent_vars(cmd);
+ int success ;
+ success = examine_parse_independent_vars(cmd);
+ if ( success != 1 ) {
+ free (dependent_vars);
+ free (totals) ;
+ }
+ return success;
}
return 1;
static int
examine_parse_independent_vars(struct cmd_examine *cmd)
{
-
+ int success;
struct factor *sf = xmalloc(sizeof(struct factor));
if ((token != T_ID || dict_lookup_var (default_dict, tokid) == NULL)
&& token != T_ALL)
- return 2;
+ {
+ free ( sf ) ;
+ return 2;
+ }
sf->indep_var[0] = parse_variable();
if ((token != T_ID || dict_lookup_var (default_dict, tokid) == NULL)
&& token != T_ALL)
- return 2;
+ {
+ free ( sf ) ;
+ return 2;
+ }
sf->indep_var[1] = parse_variable();
if ( token == '.' || token == '/' )
return 1;
- return examine_parse_independent_vars(cmd);
+ success = examine_parse_independent_vars(cmd);
+
+ if ( success != 1 )
+ free ( sf ) ;
+
+ return success;
}
output_examine();
- for ( v = 0 ; v < n_dependent_vars ; ++v )
- hsh_destroy(totals[v].ordered_data);
+
+ if ( totals )
+ {
+ int i;
+ for ( i = 0 ; i < n_dependent_vars ; ++i )
+ {
+ metrics_destroy(&totals[i]);
+ }
+ }
}
n_rows = n_dep_var * n_factors ;
if ( fctr->indep_var[1] )
- heading_columns = 3;
+ heading_columns = 3;
}
else
{
if ( 0 != compare_values(&prev, &(*fs)->id[0],
fctr->indep_var[0]->width))
{
- tab_text (tbl,
- 1,
- (i * n_factors ) + count +
- heading_rows,
- TAB_LEFT | TAT_TITLE,
- value_to_string(&(*fs)->id[0], fctr->indep_var[0])
- );
-
- if (fctr->indep_var[1] && count > 0 )
- tab_hline(tbl, TAL_1, 1, n_cols - 1,
- (i * n_factors ) + count + heading_rows);
+ tab_text (tbl,
+ 1,
+ (i * n_factors ) + count +
+ heading_rows,
+ TAB_LEFT | TAT_TITLE,
+ value_to_string(&(*fs)->id[0], fctr->indep_var[0])
+ );
+
+ if (fctr->indep_var[1] && count > 0 )
+ tab_hline(tbl, TAL_1, 1, n_cols - 1,
+ (i * n_factors ) + count + heading_rows);
}
n_rows = n_dep_var * 2 * n_extremities * n_factors;
if ( fctr->indep_var[1] )
- heading_columns = 3;
+ heading_columns = 3;
}
else
{
cn->num, 8, 0);
if ( cn->next )
- cn = cn->next;
+ cn = cn->next;
}
cn->num, 8, 0);
if ( cn->next )
- cn = cn->next;
+ cn = cn->next;
}
n_rows = n_dep_var * n_stat_rows * n_factors;
if ( fctr->indep_var[1] )
- heading_columns = 5;
+ heading_columns = 5;
}
else
{
);
populate_descriptives(tbl, heading_columns - 2,
- row, &(*fs)->m[i]);
+ row, &(*fs)->m[i]);
count++ ;
fs++;
assert(p);
+
tab_float (tbl, col + 2,
row + 4,
TAB_CENTER,
p->v,
8, 2);
}
+
tab_text (tbl, col,
row + 5,
void
box_plot_variables(const struct factor *fctr,
- struct variable **vars, int n_vars,
+ const struct variable **vars, int n_vars,
const struct variable *id)
{
+
int i;
struct factor_statistics **fs ;
{
double y_min = DBL_MAX;
double y_max = -DBL_MAX;
- struct chart ch;
+ struct chart *ch;
- chart_initialise(&ch);
+ ch = chart_create();
const char *s = factor_to_string(fctr, *fs, 0 );
- chart_write_title(&ch, s);
+ chart_write_title(ch, s);
for ( i = 0 ; i < n_vars ; ++i )
{
y_min = min(y_min, (*fs)->m[i].min);
}
- boxplot_draw_yscale(&ch, y_max, y_min);
+ boxplot_draw_yscale(ch, y_max, y_min);
for ( i = 0 ; i < n_vars ; ++i )
{
- const double box_width = (ch.data_right - ch.data_left)
+ const double box_width = (ch->data_right - ch->data_left)
/ (n_vars * 2.0 ) ;
const double box_centre = ( i * 2 + 1) * box_width
- + ch.data_left;
+ + ch->data_left;
- boxplot_draw_boxplot(&ch,
+ boxplot_draw_boxplot(ch,
box_centre, box_width,
&(*fs)->m[i],
var_to_string(vars[i]));
}
- chart_finalise(&ch);
+ chart_submit(ch);
}
-
}
box_plot_group(const struct factor *fctr,
const struct variable **vars,
int n_vars,
- const struct variable *id)
+ const struct variable *id UNUSED)
{
+
int i;
for ( i = 0 ; i < n_vars ; ++i )
{
struct factor_statistics **fs ;
- struct chart ch;
+ struct chart *ch;
- chart_initialise(&ch);
+ ch = chart_create();
- boxplot_draw_yscale(&ch, totals[i].max, totals[i].min);
+ boxplot_draw_yscale(ch, totals[i].max, totals[i].min);
if ( fctr )
{
int n_factors = 0;
int f=0;
for ( fs = fctr->fs ; *fs ; ++fs )
- ++n_factors;
+ ++n_factors;
- chart_write_title(&ch, _("Boxplot of %s vs. %s"),
+ chart_write_title(ch, _("Boxplot of %s vs. %s"),
var_to_string(vars[i]), var_to_string(fctr->indep_var[0]) );
for ( fs = fctr->fs ; *fs ; ++fs )
const char *s = factor_to_string_concise(fctr, *fs);
- const double box_width = (ch.data_right - ch.data_left)
+ const double box_width = (ch->data_right - ch->data_left)
/ (n_factors * 2.0 ) ;
const double box_centre = ( f++ * 2 + 1) * box_width
- + ch.data_left;
+ + ch->data_left;
- boxplot_draw_boxplot(&ch,
+ boxplot_draw_boxplot(ch,
box_centre, box_width,
&(*fs)->m[i],
s);
}
}
- else
+ else if ( ch )
{
- const double box_width = (ch.data_right - ch.data_left) / 3.0;
- const double box_centre = (ch.data_right + ch.data_left) / 2.0;
+ const double box_width = (ch->data_right - ch->data_left) / 3.0;
+ const double box_centre = (ch->data_right + ch->data_left) / 2.0;
- chart_write_title(&ch, _("Boxplot"));
+ chart_write_title(ch, _("Boxplot"));
- boxplot_draw_boxplot(&ch,
+ boxplot_draw_boxplot(ch,
box_centre, box_width,
&totals[i],
var_to_string(vars[i]) );
}
- chart_finalise(&ch);
+ chart_submit(ch);
}
-
}
double yfirst=0, ylast=0;
/* Normal Plot */
- struct chart np_chart;
+ struct chart *np_chart;
/* Detrended Normal Plot */
- struct chart dnp_chart;
+ struct chart *dnp_chart;
/* The slope and intercept of the ideal normal probability line */
const double slope = 1.0 / m->stddev;
if ( m->n_data == 0 )
return ;
- chart_initialise(&np_chart);
- chart_write_title(&np_chart, _("Normal Q-Q Plot of %s"), factorname);
- chart_write_xlabel(&np_chart, _("Observed Value"));
- chart_write_ylabel(&np_chart, _("Expected Normal"));
+ np_chart = chart_create();
+ dnp_chart = chart_create();
+
+ if ( !np_chart || ! dnp_chart )
+ return ;
+
+ chart_write_title(np_chart, _("Normal Q-Q Plot of %s"), factorname);
+ chart_write_xlabel(np_chart, _("Observed Value"));
+ chart_write_ylabel(np_chart, _("Expected Normal"));
- chart_initialise(&dnp_chart);
- chart_write_title(&dnp_chart, _("Detrended Normal Q-Q Plot of %s"),
+
+ chart_write_title(dnp_chart, _("Detrended Normal Q-Q Plot of %s"),
factorname);
- chart_write_xlabel(&dnp_chart, _("Observed Value"));
- chart_write_ylabel(&dnp_chart, _("Dev from Normal"));
+ chart_write_xlabel(dnp_chart, _("Observed Value"));
+ chart_write_ylabel(dnp_chart, _("Dev from Normal"));
yfirst = gsl_cdf_ugaussian_Pinv (m->wvp[0]->rank / ( m->n + 1));
ylast = gsl_cdf_ugaussian_Pinv (m->wvp[m->n_data-1]->rank / ( m->n + 1));
double x_upper = max(m->max, (ylast - intercept) / slope) ;
double slack = (x_upper - x_lower) * 0.05 ;
- chart_write_xscale(&np_chart, x_lower - slack, x_upper + slack, 5);
+ chart_write_xscale(np_chart, x_lower - slack, x_upper + slack, 5);
- chart_write_xscale(&dnp_chart, m->min, m->max, 5);
+ chart_write_xscale(dnp_chart, m->min, m->max, 5);
}
- chart_write_yscale(&np_chart, yfirst, ylast, 5);
+ chart_write_yscale(np_chart, yfirst, ylast, 5);
{
- /* We have to cache the detrended data, beacause we need to
- find its limits before we can plot it */
- double *d_data;
- d_data = xmalloc (m->n_data * sizeof(double));
- double d_max = -DBL_MAX;
- double d_min = DBL_MAX;
- for ( i = 0 ; i < m->n_data; ++i )
- {
- const double ns = gsl_cdf_ugaussian_Pinv (m->wvp[i]->rank / ( m->n + 1));
+ /* We have to cache the detrended data, beacause we need to
+ find its limits before we can plot it */
+ double *d_data;
+ d_data = xmalloc (m->n_data * sizeof(double));
+ double d_max = -DBL_MAX;
+ double d_min = DBL_MAX;
+ for ( i = 0 ; i < m->n_data; ++i )
+ {
+ const double ns = gsl_cdf_ugaussian_Pinv (m->wvp[i]->rank / ( m->n + 1));
- chart_datum(&np_chart, 0, m->wvp[i]->v.f, ns);
+ chart_datum(np_chart, 0, m->wvp[i]->v.f, ns);
- d_data[i] = (m->wvp[i]->v.f - m->mean) / m->stddev - ns;
+ d_data[i] = (m->wvp[i]->v.f - m->mean) / m->stddev - ns;
- if ( d_data[i] < d_min ) d_min = d_data[i];
- if ( d_data[i] > d_max ) d_max = d_data[i];
- }
- chart_write_yscale(&dnp_chart, d_min, d_max, 5);
+ if ( d_data[i] < d_min ) d_min = d_data[i];
+ if ( d_data[i] > d_max ) d_max = d_data[i];
+ }
+ chart_write_yscale(dnp_chart, d_min, d_max, 5);
- for ( i = 0 ; i < m->n_data; ++i )
- chart_datum(&dnp_chart, 0, m->wvp[i]->v.f, d_data[i]);
+ for ( i = 0 ; i < m->n_data; ++i )
+ chart_datum(dnp_chart, 0, m->wvp[i]->v.f, d_data[i]);
- free(d_data);
+ free(d_data);
}
- chart_line(&np_chart, slope, intercept, yfirst, ylast , CHART_DIM_Y);
- chart_line(&dnp_chart, 0, 0, m->min, m->max , CHART_DIM_X);
-
- chart_finalise(&np_chart);
- chart_finalise(&dnp_chart);
+ chart_line(np_chart, slope, intercept, yfirst, ylast , CHART_DIM_Y);
+ chart_line(dnp_chart, 0, 0, m->min, m->max , CHART_DIM_X);
+ chart_submit(np_chart);
+ chart_submit(dnp_chart);
}
/* Show the percentiles */
void
show_percentiles(struct variable **dependent_var,
- int n_dep_var,
- struct factor *fctr)
+ int n_dep_var,
+ struct factor *fctr)
{
struct tab_table *tbl;
int i;
ptiles = (*fs)->m[0].ptile_hash;
if ( fctr->indep_var[1] )
- n_heading_columns = 4;
+ n_heading_columns = 4;
}
else
{
populate_percentiles(tbl, n_heading_columns - 1,
- row, &(*fs)->m[i]);
+ row, &(*fs)->m[i]);
count++ ;
else
{
populate_percentiles(tbl, n_heading_columns - 1,
- i * n_stat_rows * n_factors + n_heading_rows,
- &totals[i]);
+ i * n_stat_rows * n_factors + n_heading_rows,
+ &totals[i]);
}
const char *
factor_to_string_concise(const struct factor *fctr,
- struct factor_statistics *fs)
+ struct factor_statistics *fs)
{