PLearn 0.1
DichotomizeVMatrix.cc
Go to the documentation of this file.
00001 // -*- C++ -*-
00002 
00003 // DichotomizeVMatrix.cc
00004 //
00005 // Copyright (C) 2007 Frederic Bastien
00006 //
00007 // Redistribution and use in source and binary forms, with or without
00008 // modification, are permitted provided that the following conditions are met:
00009 //
00010 //  1. Redistributions of source code must retain the above copyright
00011 //     notice, this list of conditions and the following disclaimer.
00012 //
00013 //  2. Redistributions in binary form must reproduce the above copyright
00014 //     notice, this list of conditions and the following disclaimer in the
00015 //     documentation and/or other materials provided with the distribution.
00016 //
00017 //  3. The name of the authors may not be used to endorse or promote
00018 //     products derived from this software without specific prior written
00019 //     permission.
00020 //
00021 // THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR
00022 // IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
00023 // OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN
00024 // NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
00025 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
00026 // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
00027 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
00028 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
00029 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
00030 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00031 //
00032 // This file is part of the PLearn library. For more information on the PLearn
00033 // library, go to the PLearn Web site at www.plearn.org
00034 
00035 // Authors: Frederic Bastien
00036 
00040 #include "DichotomizeVMatrix.h"
00041 
00042 namespace PLearn {
00043 using namespace std;
00044 
00045 
00046 PLEARN_IMPLEMENT_OBJECT(
00047     DichotomizeVMatrix,
00048     "Dichotomize variables with discrete values",
00049     "Instructions are provided with the discrete_variable_instructions option.\n"
00050     "Can map range of value to one value for each variable\n"
00051     "Variables with no specification will be kept as_is\n"
00052     );
00053 
00054 DichotomizeVMatrix::DichotomizeVMatrix():
00055     verbose(3),
00056     missing_field_error(true)
00057 /* ### Initialize all fields to their default value */
00058 {
00059     // ...
00060 
00061     // ### You may (or not) want to call build_() to finish building the object
00062     // ### (doing so assumes the parent classes' build_() have been called too
00063     // ### in the parent classes' constructors, something that you must ensure)
00064 }
00065 
00066 void DichotomizeVMatrix::getNewRow(int i, const Vec& v) const
00067 {
00068     Vec source_row(source->width());
00069     source->getRow(i,source_row);
00070     
00071     for (int source_col = 0,output_col = 0; source_col < source->width(); source_col++)
00072         {
00073             if (instruction_index[source_col] < 0)
00074             {
00075                 v[output_col] = source_row[source_col];
00076                 output_col += 1;
00077             }
00078             else
00079             {
00080                TVec<pair<real, real> > instruction_ptr = discrete_variable_instructions[instruction_index[source_col]].second;
00081                if (instruction_ptr.size() == 0) continue;
00082                bool missing = is_missing(source_row[source_col]);
00083                bool found_range = false;
00084                if(missing)
00085                    found_range=true;
00086                for (int ins_col = 0; ins_col < instruction_ptr.size(); ins_col++)
00087                {
00088                    if (missing)
00089                        v[output_col] = MISSING_VALUE;
00090                    else if (source_row[source_col] < instruction_ptr[ins_col].first 
00091                             || source_row[source_col] > instruction_ptr[ins_col].second) 
00092                        v[output_col] = 0.0;
00093                    else 
00094                    {
00095                        v[output_col] = 1.0;
00096                        found_range=true;
00097                    }
00098                    output_col += 1;
00099                }
00100                if(found_range==false && verbose>2)
00101                {
00102                    PLWARNING("DichotomizeVMatrix::getNewRow() - "
00103                              "row %d, fields %s, have a value (%f) that are outside all dichotomize range",
00104                              i,source->fieldName(source_col).c_str(),source_row[source_col]);
00105                }
00106             }    
00107         }
00108 
00109 }
00110 
00111 void DichotomizeVMatrix::declareOptions(OptionList& ol)
00112 {
00113     // ### Declare all of this object's options here.
00114     // ### For the "flags" of each option, you should typically specify
00115     // ### one of OptionBase::buildoption, OptionBase::learntoption or
00116     // ### OptionBase::tuningoption. If you don't provide one of these three,
00117     // ### this option will be ignored when loading values from a script.
00118     // ### You can also combine flags, for example with OptionBase::nosave:
00119     // ### (OptionBase::buildoption | OptionBase::nosave)
00120 
00121     declareOption(ol, "discrete_variable_instructions", &DichotomizeVMatrix::discrete_variable_instructions,
00122                   OptionBase::buildoption,
00123                   "The instructions to dichotomize the variables in the form of field_name : TVec<pair>.\n"
00124                   "The pairs are values from : to, each creating a 0, 1 variable.\n"
00125                   "Variables with no specification will be kept as_is.\n");
00126 
00127     declareOption(ol, "instruction_index", &DichotomizeVMatrix::instruction_index,
00128                   OptionBase::learntoption,
00129                   "An array that point each columns of the source matrix to its instruction.");
00130 
00131     declareOption(ol, "missing_field_error", &DichotomizeVMatrix::missing_field_error,
00132                   OptionBase::buildoption,
00133                   "If true we will generate an error is a field is"
00134                   " in the instruction but not in the source."
00135                   " Otherwise will generate a warning.");
00136 
00137     // Now call the parent class' declareOptions
00138     inherited::declareOptions(ol);
00139 }
00140 
00141 void DichotomizeVMatrix::build_()
00142 {
00143     // ### This method should do the real building of the object,
00144     // ### according to set 'options', in *any* situation.
00145     // ### Typical situations include:
00146     // ###  - Initial building of an object from a few user-specified options
00147     // ###  - Building of a "reloaded" object: i.e. from the complete set of
00148     // ###    all serialised options.
00149     // ###  - Updating or "re-building" of an object after a few "tuning"
00150     // ###    options have been modified.
00151     // ### You should assume that the parent class' build_() has already been
00152     // ### called.
00153 
00154     updateMtime(source);
00155 
00156     TVec<string> source_names = source->fieldNames();
00157 
00158     instruction_index.resize(source->width());
00159     instruction_index.fill(-1);
00160 
00161     //validate the instruction and order them as in the source matrix
00162     for (int ins_col = 0; ins_col < discrete_variable_instructions.size();
00163          ins_col++)
00164     {
00165         int source_col;
00166         for (source_col = 0; source_col < source->width(); source_col++)
00167         {
00168             if (discrete_variable_instructions[ins_col].first == source_names[source_col]) break;
00169         }
00170         if (source_col >= source->width()){
00171             if(missing_field_error)
00172                 PLERROR("In DichotomizeVMatrix::build_() -  "
00173                         "no field with this name in the source data set: %s",
00174                         (discrete_variable_instructions[ins_col].first).c_str());
00175             else
00176                 PLWARNING("In DichotomizeVMatrix::build_() -  "
00177                         "no field with this name in the source data set: %s",
00178                         (discrete_variable_instructions[ins_col].first).c_str());
00179         }
00180         else instruction_index[source_col] = ins_col;
00181     }
00182 
00183     // initialize inputsize_,targetsize_,weightsize_, width_,length()
00184     length_=source->length();
00185     int sisize=source->inputsize();
00186     int stsize=source->targetsize();
00187     int swsize=source->weightsize();
00188     int isize=0;
00189     int tsize=0;
00190     int wsize=0;
00191     int esize=0;
00192     for (int source_col = 0; source_col < sisize; source_col++)
00193     {
00194         if (instruction_index[source_col] < 0) isize++;
00195         else
00196         {
00197             TVec<pair<real, real> > instruction_ptr = 
00198                 discrete_variable_instructions[instruction_index[source_col]].second;
00199             isize += instruction_ptr.size();
00200         }
00201     }
00202     for (int source_col = sisize; 
00203          source_col < sisize + stsize; source_col++)
00204     {
00205         if (instruction_index[source_col] < 0) tsize++;
00206         else
00207         {
00208             TVec<pair<real, real> > instruction_ptr = 
00209                 discrete_variable_instructions[instruction_index[source_col]].second;
00210             tsize += instruction_ptr.size();
00211         }
00212     }
00213     for (int source_col = sisize + stsize;
00214          source_col < sisize + stsize + swsize ; source_col++)
00215     {
00216         if (instruction_index[source_col] < 0) wsize++;
00217         else
00218         {
00219             TVec<pair<real, real> > instruction_ptr = 
00220                 discrete_variable_instructions[instruction_index[source_col]].second;
00221             wsize += instruction_ptr.size();
00222         }
00223     }
00224     for (int source_col = sisize + stsize + swsize;
00225          source_col < sisize + stsize + swsize + source->extrasize() ; source_col++)
00226     {
00227         if (instruction_index[source_col] < 0) esize++;
00228         else
00229         {
00230             TVec<pair<real, real> > instruction_ptr = 
00231                 discrete_variable_instructions[instruction_index[source_col]].second;
00232             esize += instruction_ptr.size();
00233         }
00234     }
00235     defineSizes(isize, tsize, wsize, esize);
00236     width_ = isize + tsize + wsize + esize;
00237 
00238     //get the fieldnames
00239     TVec<string> fnames(width());
00240     int field_col = 0;
00241     for (int source_col = 0; source_col < source->width(); source_col++)
00242     {
00243         if (instruction_index[source_col] < 0)
00244         {
00245             fnames[field_col] = source_names[source_col];
00246             field_col += 1;
00247         }
00248         else
00249         {
00250            TVec<pair<real, real> > instruction_ptr =
00251                discrete_variable_instructions[instruction_index[source_col]].second;
00252            if (instruction_ptr.size() == 0) 
00253            {
00254                PLWARNING("In DichotomizeVMatrix::build_() -"
00255                          "instruction for field %s have no range!",
00256                          discrete_variable_instructions[instruction_index[source_col]].first.c_str());
00257                continue;
00258            }
00259            for (int ins_col = 0; ins_col < instruction_ptr.size(); ins_col++)
00260            {
00261                fnames[field_col] = source_names[source_col] + "_"
00262                                         + tostring(instruction_ptr[ins_col].first) + "_" 
00263                                         + tostring(instruction_ptr[ins_col].second);
00264                field_col += 1;
00265            }
00266         }    
00267     }
00268     declareFieldNames(fnames);
00269 }
00270 
00271 // ### Nothing to add here, simply calls build_
00272 void DichotomizeVMatrix::build()
00273 {
00274     inherited::build();
00275     build_();
00276 }
00277 
00278 void DichotomizeVMatrix::makeDeepCopyFromShallowCopy(CopiesMap& copies)
00279 {
00280     inherited::makeDeepCopyFromShallowCopy(copies);
00281 
00282     deepCopyField(discrete_variable_instructions, copies);
00283     deepCopyField(instruction_index, copies);
00284 
00285 }
00286 
00287 } // end of namespace PLearn
00288 
00289 
00290 /*
00291   Local Variables:
00292   mode:c++
00293   c-basic-offset:4
00294   c-file-style:"stroustrup"
00295   c-file-offsets:((innamespace . 0)(inline-open . 0))
00296   indent-tabs-mode:nil
00297   fill-column:79
00298   End:
00299 */
00300 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=79 :
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines