/** * FunctionTablePanel.java * @author Fabio G. Cozman * Copyright 1996 - 1999, Fabio G. Cozman, * Carnergie Mellon University, Universidade de Sao Paulo * fgcozman@usp.br, http://www.cs.cmu.edu/~fgcozman/home.html * * The JavaBayes distribution 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 2 of the License or, at your option, any later version), * provided that this notice and the name of the author appear in all * copies. Upon request to the author, some of the packages in the * JavaBayes distribution can be licensed under the GNU Lesser General * Public License as published by the Free Software Foundation (either * version 2 of the License, or (at your option) any later version). * If you're using the software, please notify fgcozman@usp.br so * that you can receive updates and patches. JavaBayes is distributed * "as is", 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 the JavaBayes distribution. If not, write to the Free * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ package JavaBayesInterface; import java.awt.*; public class FunctionTablePanel extends Panel { private String all_variable_names[]; private String all_variable_values[][]; private double table_values[]; private int parents_current_choices[]; private Panel ap, dp, pp; private Label parents_announce; private Label parents_labels[]; private Label separator_label; private Choice parent_choices[]; private TextField fields[][]; private Label first_parent_name_label; private Label first_parent_values_labels[]; private Label node_values_labels[]; private final static Color color_parents = Color.red; private final static String parents_announce_label = "Values for parents:"; /** * Default constructor for an FunctionTablePanel. */ public FunctionTablePanel(String avn[], String avv[][], double tv[]) { this.all_variable_names = avn; this.all_variable_values = avv; this.table_values = tv; // Construct the relevant panels. build_panels(); // Store the initial choices. if (all_variable_names.length > 2) { parents_current_choices = new int[parent_choices.length]; for (int i=0; i<parents_current_choices.length; i++) parents_current_choices[i] = parent_choices[i].getSelectedIndex(); } // Finally set the panel with all choices and fields. setLayout(new BorderLayout()); add("North", ap); add("Center", dp); } /** * Return the current table. */ public double[] get_table() { update_table_values(); return(table_values); } /** * Insert a new table. */ public void insert_table(double new_table[]) { table_values = new_table; int i, j, k; if (all_variable_names.length == 1) { for (j=0; j<all_variable_values[0].length; j++) fields[j][0].setText(String.valueOf(table_values[j])); } else if (all_variable_names.length == 2) { for (i=0; i<all_variable_values[0].length; i++) for (j=0; j<all_variable_values[1].length; j++) fields[i][j].setText(String.valueOf(table_values[i * all_variable_values[1].length + j])); } else { double value_set = 0.0; int parent_indexes[] = new int[all_variable_names.length]; for (k=0; k<parent_choices.length; k++) parent_indexes[k+2] = parent_choices[k].getSelectedIndex(); for (i=0; i<all_variable_values[0].length; i++) { for (j=0; j<all_variable_values[1].length; j++) { parent_indexes[0] = i; parent_indexes[1] = j; fields[i][j].setText(String.valueOf(table_values[ get_location_from_indexes(parent_indexes) ])); } } for (k=0; k<parents_current_choices.length; k++) parents_current_choices[k] = parent_choices[k].getSelectedIndex(); } } /* * Build the table panel. */ void build_panels() { build_parents_panel(); build_distribution_panel(); } /* * Build parents panel. */ private void build_parents_panel() { if (all_variable_names.length <= 2) { ap = new Panel(); return; } // Construct the panel with the values of the parents. pp = new Panel(); pp.setLayout(new GridLayout(all_variable_names.length - 2, 2)); parents_labels = new Label[all_variable_names.length - 2]; parent_choices = new Choice[all_variable_names.length - 2]; // Fill the labels and choices for the values of the parents. for (int i = 2; i<all_variable_names.length; i++) { // Get a parent parents_labels[i-2] = new Label(all_variable_names[i]); parents_labels[i-2].setForeground(color_parents); parent_choices[i-2] = new Choice(); parent_choices[i-2].setForeground(color_parents); // Fill the choice item with the values for the parent. for (int j=0; j<all_variable_values[i].length; j++) { parent_choices[i-2].addItem(all_variable_values[i][j]); } // Insert the label and choice pp.add(parents_labels[i-2]); pp.add(parent_choices[i-2]); } // Just use a panel to put the title in the parent choices. ap = new Panel(); ap.setLayout(new BorderLayout()); parents_announce = new Label(parents_announce_label, Label.CENTER); parents_announce.setForeground(color_parents); ap.add("North", parents_announce); ap.add("Center", pp); separator_label = new Label(""); ap.add("South", separator_label); } /* * Build distribution panel. */ private void build_distribution_panel() { int i, j; dp = new Panel(); node_values_labels = new Label[all_variable_values[0].length]; if (all_variable_names.length == 1) { // For a node with no parent, go directly to the distribution panel. dp.setLayout(new GridLayout(all_variable_values[0].length, 2)); fields = new TextField[all_variable_values[0].length][1]; for (j=0; j<all_variable_values[0].length; j++) { node_values_labels[j] = new Label(all_variable_values[0][j]); dp.add(node_values_labels[j]); fields[j][0] = new TextField(); fields[j][0].setText(String.valueOf(table_values[j])); dp.add(fields[j][0]); } } else { // For one or more parents, create a two-dimensional table. dp.setLayout(new GridLayout(all_variable_values[0].length + 1, all_variable_values[1].length + 1)); fields = new TextField[all_variable_values[0].length][all_variable_values[1].length]; first_parent_name_label = new Label(all_variable_names[1]); first_parent_name_label.setForeground(color_parents); dp.add(first_parent_name_label); first_parent_values_labels = new Label[all_variable_values[1].length]; for (i=0; i<all_variable_values[1].length; i++) { first_parent_values_labels[i] = new Label(all_variable_values[1][i]); first_parent_values_labels[i].setForeground(color_parents); dp.add(first_parent_values_labels[i]); } // Auxiliary jump; used to compute location of table values. int jump = 1; if (all_variable_names.length > 1) { for (i=2; i<all_variable_names.length; i++) jump *= all_variable_values[i].length; } for (j=0; j<all_variable_values[0].length; j++) { node_values_labels[j] = new Label(all_variable_values[0][j]); dp.add(node_values_labels[j]); for (i=0; i<all_variable_values[1].length; i++) { fields[j][i] = new TextField(); fields[j][i].setText(String.valueOf( table_values[(j * all_variable_values[1].length + i) * jump])); dp.add(fields[j][i]); } } } } /** * Handle events in the panel. */ public boolean action(Event evt, Object arg) { int i, j, k; int starting_index; double value_set = 0.0; // In case the node has more than one // parent, check whether parent values // have been changed. if (all_variable_names.length > 2) { for (i=0; i<parent_choices.length; i++) { if (evt.target == parent_choices[i]) { update_table_for_parents(); return(true); } } } return(super.action(evt, arg)); } /* * Update the table when the parents change. */ private void update_table_for_parents() { int i, j, k; if (all_variable_names.length == 1) { for (j=0; j<all_variable_values[0].length; j++) fields[j][0].setText(String.valueOf(table_values[j])); } else if (all_variable_names.length == 2) { for (i=0; i<all_variable_values[0].length; i++) for (j=0; j<all_variable_values[1].length; j++) fields[i][j].setText(String.valueOf(table_values[i * all_variable_values[1].length + j])); } else { double value_set = 0.0; int parent_indexes[] = new int[all_variable_names.length]; for (k=0; k<parent_choices.length; k++) parent_indexes[k+2] = parents_current_choices[k]; for (i=0; i<fields.length; i++) { for (j=0; j<fields[i].length; j++) { try { value_set = (new Double( fields[i][j].getText() ).doubleValue() ); parent_indexes[0] = i; parent_indexes[1] = j; table_values[get_location_from_indexes(parent_indexes)] = value_set; } catch (NumberFormatException e) { } } } for (k=0; k<parent_choices.length; k++) parent_indexes[k+2] = parent_choices[k].getSelectedIndex(); for (i=0; i<all_variable_values[0].length; i++) { for (j=0; j<all_variable_values[1].length; j++) { parent_indexes[0] = i; parent_indexes[1] = j; fields[i][j].setText(String.valueOf(table_values[ get_location_from_indexes(parent_indexes) ])); } } for (k=0; k<parents_current_choices.length; k++) parents_current_choices[k] = parent_choices[k].getSelectedIndex(); } } /* * Update the table values. */ private void update_table_values() { int i, j, k; if (all_variable_names.length == 1) { for (i=0; i<fields.length; i++) { try { table_values[i] = (new Double( fields[i][0].getText() ).doubleValue() ); } catch (NumberFormatException e) { } } } else if (all_variable_names.length == 2) { for (i=0; i<fields.length; i++) { for (j=0; j<fields[i].length; j++) { try { table_values[i * all_variable_values[1].length + j] = (new Double( fields[i][j].getText() ).doubleValue() ); } catch (NumberFormatException e) { } } } } else { double value_set = 0.0; int parent_indexes[] = new int[all_variable_names.length]; for (k=0; k<parent_choices.length; k++) parent_indexes[k+2] = parent_choices[k].getSelectedIndex(); for (i=0; i<fields.length; i++) { for (j=0; j<fields[i].length; j++) { try { value_set = (new Double( fields[i][j].getText() ).doubleValue() ); parent_indexes[0] = i; parent_indexes[1] = j; table_values[get_location_from_indexes(parent_indexes)] = value_set; } catch (NumberFormatException e) { } } } } } /* * Determine the index of a given location. */ private int get_location_from_indexes(int indexes[]) { int pos = 0, jump = 1; for (int i=(all_variable_names.length-1); i>=0; i--) { pos += indexes[i] * jump; jump *= all_variable_values[i].length; } return(pos); } }