My favorites | Sign in
Project Home Downloads Wiki Issues Source
Checkout   Browse   Changes    
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
package org.shapelogic.imageprocessing;

import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.NoSuchElementException;

import org.shapelogic.calculation.RecursiveContext;
import org.shapelogic.logic.CommonLogicExpressions;
import org.shapelogic.machinelearning.ExampleNeuralNetwork;
import org.shapelogic.machinelearning.FFNeuralNetworkStream;
import org.shapelogic.machinelearning.FFNeuralNetworkWeights;
import org.shapelogic.machinelearning.FFNeuralNetworkWeightsParser;
import org.shapelogic.polygon.Polygon;
import org.shapelogic.reporting.BaseTableBuilder;
import org.shapelogic.reporting.TableDefinition;
import org.shapelogic.streamlogic.LoadLetterStreams;
import org.shapelogic.streamlogic.StreamNames;
import org.shapelogic.streams.NumberedStream;
import org.shapelogic.streams.StreamFactory;
import org.shapelogic.util.Headings;

/** Same vectorizer as MaxDistanceVectorizer, but logic implemented with streams.
* <br />
*
* @author Sami Badawi
*
*/
public class StreamVectorizer extends BaseMaxDistanceVectorizer implements RecursiveContext {
protected Map _context = new HashMap();
protected LoadLetterStreams loadLetterStreams;
protected NumberedStream<String> _categorizer;

protected boolean _useNeuralNetwork;
protected String _neuralNetworkFile;

protected BaseTableBuilder _tableBuilder;
protected TableDefinition _tableDefinition;
protected List<String> _printListOverwrite;

protected boolean _displayAll = false;
protected boolean _displayResultTable = false;

/** This does really not belong in a vectorizer. */
@Override
protected void matchLines() {
if (_categorizer == null) //To be backwards compatible
_categorizer = StreamFactory.findNumberedStream(StreamNames.LETTERS, this);
String message = "";
StringBuffer internalInfo = new StringBuffer();
if (_displayInternalInfo || _displayAll) {
internalInfo.append("\n===================Internal info for skeletonized lines===================\n");
}
for (int i = 0; hasNext(); i++)
{
String currentMatch = _categorizer.next();
if (i != 0)
message += "; ";
message += currentMatch;
if (currentMatch == null || "".equals(currentMatch))
System.out.println("\n\nMatch failed for this:\n" + _cleanedupPolygon);
if (_displayInternalInfo || _displayAll) {
Polygon currentPolygon = _stream.get(i);
internalInfo.append(currentPolygon.toString());
}
}
_matchingOH = message;
if (_matchingOH == null) {
System.out.println("\n\nLetter matched failed for this:\n" + _cleanedupPolygon);
}
showMessage("","Letter match result: " + _matchingOH);
if (_displayInternalInfo || _displayAll) {
showMessage("InternalInfo for skeletonized lines",internalInfo.toString());
}
}

protected FFNeuralNetworkWeights readFFNeuralNetworkWeights() {
FFNeuralNetworkWeightsParser parser = new FFNeuralNetworkWeightsParser();
try {
if (_neuralNetworkFile == null || _neuralNetworkFile.trim().length() == 0)
return null;
FFNeuralNetworkWeights result = parser.parse(_neuralNetworkFile);
if (result == null)
showMessage("Parsing error","File: " + _neuralNetworkFile +
"\n has error, it returns FFNeuralNetworkWeights == null.");
return result;
} catch (Exception e) {
//Ignore it for now and use default instead.
showMessage("Parsing error","File: " + _neuralNetworkFile +
"\n has error: " + e.getMessage());
return null;
}
}

/** Method to override if you want to define your own rule set.<br />
*
* The default network is very simple it is marking particles Tall, Flat
* based on their aspect ratio.
*/
protected void defineRules() {
FFNeuralNetworkWeights fFNeuralNetworkWeights =
readFFNeuralNetworkWeights();
if (fFNeuralNetworkWeights != null &&
fFNeuralNetworkWeights.getRulePredicates().size() == 0) {
showMessage("Missing rules","File: " + _neuralNetworkFile +
"\n has missing letter definition rules, using default instead.");
fFNeuralNetworkWeights = null;
}
if (fFNeuralNetworkWeights != null)
loadLetterStreams.loadUserDefinedSymbolStreams(
fFNeuralNetworkWeights, StreamNames.LETTERS);
else
loadLetterStreams.loadLetterStream(null);
_categorizer = StreamFactory.findNumberedStream(StreamNames.LETTERS, this);
}

/** Method to override if you want to define your own neural network.<br />
*
* The default network is very simple it is marking particles Dark or Light.
*/
protected void defineNeuralNetwork() {
loadLetterStreams.loadLetterStream(null);
FFNeuralNetworkWeights fFNeuralNetworkWeights =
readFFNeuralNetworkWeights();
if (fFNeuralNetworkWeights != null &&
fFNeuralNetworkWeights.getWeights().length == 0) {
showMessage("Missing weights","File: " + _neuralNetworkFile +
"\n has missing neural network weights, using default instead.");
fFNeuralNetworkWeights = null;
}
if (fFNeuralNetworkWeights == null) {
String[] objectHypotheses = new String[] {"No holes", "Holes"};
String[] inputStreamName = {CommonLogicExpressions.HOLE_COUNT};
double[][] weights = ExampleNeuralNetwork.makeSmallerThanGreaterThanNeuralNetwork(0.5);
fFNeuralNetworkWeights = new FFNeuralNetworkWeights(
Arrays.asList(inputStreamName),
Arrays.asList(objectHypotheses),
weights);
String[] printArray = {"Category", "Points", "lineCount", "holeCount"};
List<String> printList = fFNeuralNetworkWeights.getPrintList();
for (String element: printArray)
printList.add(element);
}
FFNeuralNetworkStream neuralNetworkStream = new FFNeuralNetworkStream(
fFNeuralNetworkWeights,this);
_categorizer = neuralNetworkStream.getOutputStream();
if (0 < fFNeuralNetworkWeights.getPrintList().size())
_printListOverwrite = fFNeuralNetworkWeights.getPrintList();
}

/** Use this to setup all the needed streams.
*/
@Override
public void init() {
_context.clear();
super.init();
_context.put(StreamNames.POLYGONS, getStream());
loadLetterStreams = new LoadLetterStreams(this);
matchSetup();
}

/** In order to match a different alphabet override this.
*/
public void matchSetup() {
if (_useNeuralNetwork) {
defineNeuralNetwork();
}
else {
defineRules();
}
}

@Override
public void run() {
try {
init();
matchLines();
if (_displayResultTable || _displayAll)
printTable();
} catch (NoSuchElementException e) {
_errorMessage = e.getMessage();
showMessage("Missing element", e.getMessage());
}
}

@Override
public Map getContext() {
return _context;
}

@Override
public RecursiveContext getParentContext() {
return null;
}

public void printTable() {
defaultStreamDefinitions();
customStreamDefinitions();
categorizeStreams();
defaultColumnDefinitions();
setupTableBuilder();
populateResultsTable();
displayResultsTable();
}

protected void defaultStreamDefinitions() {
}

protected void categorizeStreams() {
}

protected void customStreamDefinitions() {
_tableDefinition = new TableDefinition(null);
_tableDefinition.addDefinition(_categorizer, Headings.CATEGORY);
_tableDefinition.addDefinition(CommonLogicExpressions.POINT_COUNT,"Points");
_tableDefinition.addDefinition(CommonLogicExpressions.LINE_COUNT,"Lines");
_tableDefinition.addDefinition(CommonLogicExpressions.HOLE_COUNT, "Holes");
_tableDefinition.addDefinition(CommonLogicExpressions.T_JUNCTION_LEFT_POINT_COUNT,"T_left");
_tableDefinition.addDefinition(CommonLogicExpressions.T_JUNCTION_RIGHT_POINT_COUNT,"T_right");
_tableDefinition.addDefinition(CommonLogicExpressions.END_POINT_BOTTOM_POINT_COUNT, "End_bottom");
_tableDefinition.addDefinition(CommonLogicExpressions.HORIZONTAL_LINE_COUNT, "Horizontal");
_tableDefinition.addDefinition(CommonLogicExpressions.VERTICAL_LINE_COUNT, "Vertical");
_tableDefinition.addDefinition(CommonLogicExpressions.END_POINT_COUNT, null);
_tableDefinition.addDefinition(CommonLogicExpressions.SOFT_POINT_COUNT, null);

}

protected void defaultColumnDefinitions() {
}

protected void setupTableBuilder() {
}

protected void populateResultsTable(){
List<Polygon> polygons = _stream.getList();
_tableDefinition.findNonEmptyColumns(this);
if (_printListOverwrite != null)
_tableDefinition.sort(_printListOverwrite, this);
_tableBuilder.buildHeadline();
for (int i=0;i<polygons.size();i++) {
if (populateResultsTableRow(i))
;
}
}

protected void displayResultsTable() {
_tableBuilder = new BaseTableBuilder(_tableDefinition);
}

protected boolean populateResultsTableRow(int index) {
return true;
}

public void setUseNeuralNetwork(boolean useNeuralNetwork) {
_useNeuralNetwork = useNeuralNetwork;
}

public void setNeuralNetworkFile(String neuralNetworkFile) {
_neuralNetworkFile = neuralNetworkFile;
}

}

Change log

r1159 by sami.badawi on May 14, 2009   Diff
Better error handling.
Go to: 
Project members, sign in to write a code review

Older revisions

r1142 by sami.badawi on May 12, 2009   Diff
Set fall back in case of missing
configuration data.
r1128 by sami.badawi on May 11, 2009   Diff
Added neural networks test with
external data configuration file to
StreamVectorizer.
r1125 by sami.badawi on May 10, 2009   Diff
Better input dialog.
All revisions of this file

File info

Size: 9498 bytes, 263 lines

File properties

svn:mime-type
text/plain
Powered by Google Project Hosting