001 package org.maltparser.core.syntaxgraph.feature; 002 003 import org.maltparser.core.exception.MaltChainedException; 004 import org.maltparser.core.feature.FeatureException; 005 import org.maltparser.core.feature.function.AddressFunction; 006 import org.maltparser.core.feature.function.FeatureFunction; 007 import org.maltparser.core.feature.value.AddressValue; 008 import org.maltparser.core.feature.value.FeatureValue; 009 import org.maltparser.core.feature.value.SingleFeatureValue; 010 import org.maltparser.core.io.dataformat.ColumnDescription; 011 import org.maltparser.core.io.dataformat.DataFormatInstance; 012 import org.maltparser.core.symbol.SymbolTable; 013 import org.maltparser.core.symbol.SymbolTableHandler; 014 import org.maltparser.core.symbol.nullvalue.NullValues.NullValueId; 015 import org.maltparser.core.syntaxgraph.SyntaxGraphException; 016 import org.maltparser.core.syntaxgraph.node.DependencyNode; 017 /** 018 * 019 * @author Johan Hall 020 * @since 1.1 021 **/ 022 public class InputArcFeature implements FeatureFunction { 023 protected AddressFunction addressFunction1; 024 protected AddressFunction addressFunction2; 025 protected ColumnDescription column; 026 protected DataFormatInstance dataFormatInstance; 027 protected SymbolTableHandler tableHandler; 028 protected SymbolTable table; 029 protected SingleFeatureValue featureValue; 030 031 032 public InputArcFeature(DataFormatInstance dataFormatInstance, SymbolTableHandler tableHandler) throws MaltChainedException { 033 super(); 034 setDataFormatInstance(dataFormatInstance); 035 setTableHandler(tableHandler); 036 setFeatureValue(new SingleFeatureValue(this)); 037 } 038 039 public void initialize(Object[] arguments) throws MaltChainedException { 040 if (arguments.length != 3) { 041 throw new FeatureException("Could not initialize InputArcFeature: number of arguments are not correct. "); 042 } 043 // Checks that the two arguments are address functions 044 045 if (!(arguments[0] instanceof String)) { 046 throw new FeatureException("Could not initialize InputArcFeature: the first argument is not a string. "); 047 } 048 if (!(arguments[1] instanceof AddressFunction)) { 049 throw new SyntaxGraphException("Could not initialize InputArcFeature: the second argument is not an address function. "); 050 } 051 if (!(arguments[2] instanceof AddressFunction)) { 052 throw new SyntaxGraphException("Could not initialize InputArcFeature: the third argument is not an address function. "); 053 } 054 setAddressFunction1((AddressFunction)arguments[1]); 055 setAddressFunction2((AddressFunction)arguments[2]); 056 057 setColumn(dataFormatInstance.getColumnDescriptionByName((String)arguments[0])); 058 setSymbolTable(tableHandler.addSymbolTable("ARC_"+column.getName(),ColumnDescription.INPUT, "one")); 059 table.addSymbol("LEFT"); 060 table.addSymbol("RIGHT"); 061 } 062 063 public Class<?>[] getParameterTypes() { 064 Class<?>[] paramTypes = { java.lang.String.class, org.maltparser.core.feature.function.AddressFunction.class, org.maltparser.core.feature.function.AddressFunction.class }; 065 return paramTypes; 066 } 067 068 public int getCode(String symbol) throws MaltChainedException { 069 return table.getSymbolStringToCode(symbol); 070 } 071 072 073 public FeatureValue getFeatureValue() { 074 return featureValue; 075 } 076 077 078 public String getSymbol(int code) throws MaltChainedException { 079 return table.getSymbolCodeToString(code); 080 } 081 082 083 public void updateCardinality() throws MaltChainedException { 084 featureValue.setCardinality(table.getValueCounter()); 085 } 086 087 public void update() throws MaltChainedException { 088 // Retrieve the address value 089 final AddressValue arg1 = addressFunction1.getAddressValue(); 090 final AddressValue arg2 = addressFunction2.getAddressValue(); 091 if (arg1.getAddress() != null && arg1.getAddressClass() == org.maltparser.core.syntaxgraph.node.DependencyNode.class && 092 arg2.getAddress() != null && arg2.getAddressClass() == org.maltparser.core.syntaxgraph.node.DependencyNode.class) { 093 DependencyNode node1 = (DependencyNode)arg1.getAddress(); 094 DependencyNode node2 = (DependencyNode)arg2.getAddress(); 095 try { 096 int head1 = Integer.parseInt(node1.getLabelSymbol(column.getSymbolTable())); 097 int head2 = Integer.parseInt(node2.getLabelSymbol(column.getSymbolTable())); 098 if (!node1.isRoot() && head1 == node2.getIndex()) { 099 featureValue.setCode(table.getSymbolStringToCode("LEFT")); 100 featureValue.setSymbol("LEFT"); 101 featureValue.setKnown(true); 102 featureValue.setNullValue(false); 103 } else if (!node2.isRoot() && head2 == node1.getIndex()) { 104 featureValue.setCode(table.getSymbolStringToCode("RIGHT")); 105 featureValue.setSymbol("RIGHT"); 106 featureValue.setKnown(true); 107 featureValue.setNullValue(false); 108 } else { 109 featureValue.setCode(table.getNullValueCode(NullValueId.NO_NODE)); 110 featureValue.setSymbol(table.getNullValueSymbol(NullValueId.NO_NODE)); 111 featureValue.setKnown(true); 112 featureValue.setNullValue(true); 113 } 114 } catch (NumberFormatException e) { 115 throw new FeatureException("The index of the feature must be an integer value. ", e); 116 } 117 } else { 118 featureValue.setCode(table.getNullValueCode(NullValueId.NO_NODE)); 119 featureValue.setSymbol(table.getNullValueSymbol(NullValueId.NO_NODE)); 120 featureValue.setKnown(true); 121 featureValue.setNullValue(true); 122 } 123 } 124 125 public ColumnDescription getColumn() { 126 return column; 127 } 128 129 public void setColumn(ColumnDescription column) throws MaltChainedException { 130 if (column.getType() != ColumnDescription.INTEGER) { 131 throw new FeatureException("InputArc feature column must be of type integer. "); 132 } 133 this.column = column; 134 } 135 136 /** 137 * Returns the address function 1 (argument 1) 138 * 139 * @return the address function 1 (argument 1) 140 */ 141 public AddressFunction getAddressFunction1() { 142 return addressFunction1; 143 } 144 145 146 /** 147 * Sets the address function 1 (argument 1) 148 * 149 * @param addressFunction1 a address function 1 (argument 1) 150 */ 151 public void setAddressFunction1(AddressFunction addressFunction1) { 152 this.addressFunction1 = addressFunction1; 153 } 154 155 /** 156 * Returns the address function 2 (argument 2) 157 * 158 * @return the address function 1 (argument 2) 159 */ 160 public AddressFunction getAddressFunction2() { 161 return addressFunction2; 162 } 163 164 /** 165 * Sets the address function 2 (argument 2) 166 * 167 * @param addressFunction2 a address function 2 (argument 2) 168 */ 169 public void setAddressFunction2(AddressFunction addressFunction2) { 170 this.addressFunction2 = addressFunction2; 171 } 172 173 public DataFormatInstance getDataFormatInstance() { 174 return dataFormatInstance; 175 } 176 177 public void setDataFormatInstance(DataFormatInstance dataFormatInstance) { 178 this.dataFormatInstance = dataFormatInstance; 179 } 180 181 public void setFeatureValue(SingleFeatureValue featureValue) { 182 this.featureValue = featureValue; 183 } 184 185 public SymbolTable getSymbolTable() { 186 return table; 187 } 188 189 public void setSymbolTable(SymbolTable table) { 190 this.table = table; 191 } 192 193 public SymbolTableHandler getTableHandler() { 194 return tableHandler; 195 } 196 197 public void setTableHandler(SymbolTableHandler tableHandler) { 198 this.tableHandler = tableHandler; 199 } 200 201 public boolean equals(Object obj) { 202 if (!(obj instanceof InputArcFeature)) { 203 return false; 204 } 205 if (!obj.toString().equals(this.toString())) { 206 return false; 207 } 208 return true; 209 } 210 211 public String toString() { 212 return "InputArc(" + column.getName() + ")"; 213 } 214 }