001    package org.maltparser.core.feature.map;
002    
003    import org.maltparser.core.exception.MaltChainedException;
004    import org.maltparser.core.feature.FeatureException;
005    import org.maltparser.core.feature.function.FeatureFunction;
006    import org.maltparser.core.feature.function.FeatureMapFunction;
007    import org.maltparser.core.feature.value.FeatureValue;
008    import org.maltparser.core.feature.value.FunctionValue;
009    import org.maltparser.core.feature.value.MultipleFeatureValue;
010    import org.maltparser.core.feature.value.SingleFeatureValue;
011    import org.maltparser.core.io.dataformat.ColumnDescription;
012    import org.maltparser.core.io.dataformat.DataFormatInstance;
013    import org.maltparser.core.symbol.SymbolTable;
014    import org.maltparser.core.symbol.SymbolTableHandler;
015    /**
016    *
017    *
018    * @author Johan Hall
019    */
020    public class SuffixFeature implements FeatureMapFunction {
021            protected FeatureFunction parentFeature;
022            protected MultipleFeatureValue multipleFeatureValue;
023            protected SymbolTableHandler tableHandler;
024            protected SymbolTable table;
025            protected DataFormatInstance dataFormatInstance;
026            protected ColumnDescription column;
027            protected int suffixLength;
028    
029            public SuffixFeature(DataFormatInstance dataFormatInstance) throws MaltChainedException {
030                    super();
031                    setDataFormatInstance(dataFormatInstance);
032                    multipleFeatureValue = new MultipleFeatureValue(this);
033            }
034            
035            public void initialize(Object[] arguments) throws MaltChainedException {
036                    if (arguments.length != 2) {
037                            throw new FeatureException("Could not initialize SuffixFeature: number of arguments are not correct. ");
038                    }
039                    if (!(arguments[0] instanceof FeatureFunction)) {
040                            throw new FeatureException("Could not initialize SuffixFeature: the first argument is not a feature. ");
041                    }
042                    if (!(arguments[1] instanceof Integer)) {
043                            throw new FeatureException("Could not initialize SuffixFeature: the second argument is not a string. ");
044                    }
045                    setParentFeature((FeatureFunction)arguments[0]);
046                    setSuffixLength(((Integer)arguments[1]).intValue());
047                    ColumnDescription parentColumn = dataFormatInstance.getColumnDescriptionByName(parentFeature.getSymbolTable().getName());
048                    if (parentColumn.getType() != ColumnDescription.STRING) {
049                            throw new FeatureException("Could not initialize SuffixFeature: the first argument must be a string. ");
050                    }
051                    setColumn(dataFormatInstance.addInternalColumnDescription("SUFFIX_"+suffixLength+"_"+parentFeature.getSymbolTable().getName(), parentColumn));
052                    setSymbolTable(column.getSymbolTable());
053    //              setSymbolTable(tableHandler.addSymbolTable("SUFFIX_"+suffixLength+"_"+parentFeature.getSymbolTable().getName(), parentFeature.getSymbolTable()));
054            }
055            
056            public Class<?>[] getParameterTypes() {
057                    Class<?>[] paramTypes = { org.maltparser.core.syntaxgraph.feature.InputColumnFeature.class, java.lang.Integer.class };
058                    return paramTypes; 
059            }
060            
061            public FeatureValue getFeatureValue() {
062                    return multipleFeatureValue;
063            }
064            
065            public int getCode(String symbol) throws MaltChainedException {
066                    return table.getSymbolStringToCode(symbol);
067            }
068    
069            public String getSymbol(int code) throws MaltChainedException {
070                    return table.getSymbolCodeToString(code);
071            }
072    
073            public void update() throws MaltChainedException {
074                    parentFeature.update();
075                    FunctionValue value = parentFeature.getFeatureValue();
076                    if (value instanceof SingleFeatureValue) {
077                            String symbol = ((SingleFeatureValue)value).getSymbol();
078                            if (((FeatureValue)value).isNullValue()) {
079                                    multipleFeatureValue.addFeatureValue(parentFeature.getSymbolTable().getSymbolStringToCode(symbol), symbol);
080                                    multipleFeatureValue.setNullValue(true);
081                            } else {
082                                    String suffixStr;
083                                    if (symbol.length()-suffixLength > 0) {
084                                            suffixStr = symbol.substring(symbol.length()-suffixLength);
085                                    } else {
086                                            suffixStr = symbol;
087                                    }
088                                    int code = table.addSymbol(suffixStr);
089                                    multipleFeatureValue.addFeatureValue(code, suffixStr);
090                                    multipleFeatureValue.setNullValue(false);
091                            }
092                    } else if (value instanceof MultipleFeatureValue) {
093                            multipleFeatureValue.reset();
094                            if (((MultipleFeatureValue)value).isNullValue()) {
095                                    multipleFeatureValue.addFeatureValue(parentFeature.getSymbolTable().getSymbolStringToCode(((MultipleFeatureValue)value).getFirstSymbol()), ((MultipleFeatureValue)value).getFirstSymbol());
096                                    multipleFeatureValue.setNullValue(true);
097                            } else {
098                                    for (String symbol : ((MultipleFeatureValue)value).getSymbols()) {
099                                            String suffixStr;
100                                            if (symbol.length()-suffixLength > 0) {
101                                                    suffixStr = symbol.substring(symbol.length()-suffixLength);
102                                            } else {
103                                                    suffixStr = symbol;
104                                            }
105                                            int code = table.addSymbol(suffixStr);
106                                            multipleFeatureValue.addFeatureValue(code, suffixStr);
107                                            multipleFeatureValue.setNullValue(true);
108                                    }
109                            }
110                    }
111            }
112    
113            public FeatureFunction getParentFeature() {
114                    return parentFeature;
115            } 
116            
117            public void setParentFeature(FeatureFunction feature) {
118                    this.parentFeature = feature;
119            }
120            
121            public int getSuffixLength() {
122                    return suffixLength;
123            }
124    
125            public void setSuffixLength(int suffixLength) {
126                    this.suffixLength = suffixLength;
127            }
128    
129            public SymbolTableHandler getTableHandler() {
130                    return dataFormatInstance.getSymbolTables();
131            }
132            
133            public SymbolTable getSymbolTable() {
134                    return table;
135            }
136    
137            public void setSymbolTable(SymbolTable table) {
138                    this.table = table;
139            }
140            
141            public DataFormatInstance getDataFormatInstance() {
142                    return dataFormatInstance;
143            }
144    
145            public void setDataFormatInstance(DataFormatInstance dataFormatInstance) {
146                    this.dataFormatInstance = dataFormatInstance;
147            }
148            
149            public ColumnDescription getColumn() {
150                    return column;
151            }
152            
153            protected void setColumn(ColumnDescription column) {
154                    this.column = column;
155            }
156            
157            public  int getType() {
158                    return column.getType();
159            }
160            
161            public String getMapIdentifier() {
162                    return getSymbolTable().getName();
163            }
164            
165            public boolean equals(Object obj) {
166                    if (this == obj)
167                            return true;
168                    if (obj == null)
169                            return false;
170                    if (getClass() != obj.getClass())
171                            return false;
172                    return obj.toString().equals(this.toString());
173            }
174            
175            public String toString() {
176                    final StringBuilder sb = new StringBuilder();
177                    sb.append("Suffix(");
178                    sb.append(parentFeature.toString());
179                    sb.append(", ");
180                    sb.append(suffixLength);
181                    sb.append(')');
182                    return sb.toString();
183            }
184    }