root / org.gvsig.toolbox / trunk / org.gvsig.toolbox / org.gvsig.toolbox.algorithm / src / main / java / es / unex / sextante / statisticalMethods / regression / RegressionAlgorithm.java @ 59
History | View | Annotate | Download (7.95 KB)
1 | 59 | nbrodin | package es.unex.sextante.statisticalMethods.regression; |
---|---|---|---|
2 | |||
3 | import java.text.DecimalFormat; |
||
4 | |||
5 | import com.vividsolutions.jts.geom.Coordinate; |
||
6 | import com.vividsolutions.jts.geom.Geometry; |
||
7 | |||
8 | import es.unex.sextante.additionalInfo.AdditionalInfoVectorLayer; |
||
9 | import es.unex.sextante.core.AnalysisExtent; |
||
10 | import es.unex.sextante.core.GeoAlgorithm; |
||
11 | import es.unex.sextante.core.Sextante; |
||
12 | import es.unex.sextante.dataObjects.IFeature; |
||
13 | import es.unex.sextante.dataObjects.IFeatureIterator; |
||
14 | import es.unex.sextante.dataObjects.IRasterLayer; |
||
15 | import es.unex.sextante.dataObjects.IVectorLayer; |
||
16 | import es.unex.sextante.docEngines.html.HTMLDoc; |
||
17 | import es.unex.sextante.exceptions.GeoAlgorithmExecutionException; |
||
18 | import es.unex.sextante.exceptions.IteratorException; |
||
19 | import es.unex.sextante.exceptions.OptionalParentParameterException; |
||
20 | import es.unex.sextante.exceptions.RepeatedParameterNameException; |
||
21 | import es.unex.sextante.exceptions.UndefinedParentParameterNameException; |
||
22 | import es.unex.sextante.math.regression.Regression; |
||
23 | import es.unex.sextante.outputs.OutputVectorLayer; |
||
24 | import es.unex.sextante.rasterWrappers.GridCell; |
||
25 | |||
26 | public class RegressionAlgorithm |
||
27 | extends
|
||
28 | GeoAlgorithm { |
||
29 | |||
30 | public static final String METHOD = "METHOD"; |
||
31 | public static final String RESIDUALS = "RESIDUALS"; |
||
32 | public static final String RESULT = "RESULT"; |
||
33 | public static final String FIELD = "FIELD"; |
||
34 | public static final String POINTS = "POINTS"; |
||
35 | public static final String RASTER = "RASTER"; |
||
36 | public static final String REGRESSION_DATA = "REGRESSION_DATA"; |
||
37 | |||
38 | private int m_iField; |
||
39 | private IVectorLayer m_Residuals;
|
||
40 | private IRasterLayer m_Window;
|
||
41 | private IRasterLayer m_Result;
|
||
42 | Regression m_Regression; |
||
43 | private IVectorLayer m_Points;
|
||
44 | |||
45 | |||
46 | @Override
|
||
47 | public void defineCharacteristics() { |
||
48 | |||
49 | final String sMethod[] = { "y = a + b * x", "y = a + b / x", "y = a / (b - x)", "y = a * x^b", "y = a e^(b * x)", |
||
50 | "y = a + b * ln(x)" };
|
||
51 | |||
52 | this.setName(Sextante.getText("Regression")); |
||
53 | setGroup(Sextante.getText("Statistical_methods"));
|
||
54 | setUserCanDefineAnalysisExtent(true);
|
||
55 | |||
56 | try {
|
||
57 | m_Parameters.addInputVectorLayer(POINTS, Sextante.getText("Points"), AdditionalInfoVectorLayer.SHAPE_TYPE_POINT, true); |
||
58 | m_Parameters.addTableField(FIELD, Sextante.getText("Field"), "POINTS"); |
||
59 | m_Parameters.addInputRasterLayer(RASTER, Sextante.getText("Raster_layer"), true); |
||
60 | m_Parameters.addSelection(METHOD, Sextante.getText("Equation"), sMethod);
|
||
61 | addOutputRasterLayer(RESULT, Sextante.getText("Result"));
|
||
62 | addOutputVectorLayer(RESIDUALS, Sextante.getText("Residuals"), OutputVectorLayer.SHAPE_TYPE_POINT);
|
||
63 | addOutputText(REGRESSION_DATA, Sextante.getText("Regression_values"));
|
||
64 | } |
||
65 | catch (final RepeatedParameterNameException e) { |
||
66 | Sextante.addErrorToLog(e); |
||
67 | } |
||
68 | catch (final UndefinedParentParameterNameException e) { |
||
69 | Sextante.addErrorToLog(e); |
||
70 | } |
||
71 | catch (final OptionalParentParameterException e) { |
||
72 | Sextante.addErrorToLog(e); |
||
73 | } |
||
74 | |||
75 | } |
||
76 | |||
77 | |||
78 | @Override
|
||
79 | public boolean processAlgorithm() throws GeoAlgorithmExecutionException { |
||
80 | |||
81 | final String sFieldNames[] = { Sextante.getText("Real_value"), Sextante.getText("Predictor_value"), |
||
82 | Sextante.getText("Estimated_value"), Sextante.getText("Diference"), Sextante.getText("Variance") }; |
||
83 | final Class types[] = { Double.class, Double.class, Double.class, Double.class, Double.class }; |
||
84 | |||
85 | m_iField = m_Parameters.getParameterValueAsInt(FIELD); |
||
86 | m_Points = m_Parameters.getParameterValueAsVectorLayer(POINTS); |
||
87 | |||
88 | if (m_Points.getShapesCount() == 0) { |
||
89 | throw new GeoAlgorithmExecutionException(Sextante.getText("Invalid_input_data")); |
||
90 | } |
||
91 | |||
92 | m_Window = m_Parameters.getParameterValueAsRasterLayer(RASTER); |
||
93 | |||
94 | m_Result = getNewRasterLayer(RESULT, Sextante.getText("Regression"), IRasterLayer.RASTER_DATA_TYPE_DOUBLE);
|
||
95 | final AnalysisExtent extent = m_Result.getWindowGridExtent();
|
||
96 | m_Window.setWindowExtent(extent); |
||
97 | |||
98 | m_Residuals = getNewVectorLayer(RESIDUALS, Sextante.getText("Residuals"), IVectorLayer.SHAPE_TYPE_POINT, types, sFieldNames);
|
||
99 | |||
100 | calculateRegression(); |
||
101 | calculateResultingGrid(); |
||
102 | calculateResiduals(); |
||
103 | addRegressionInfo(); |
||
104 | |||
105 | return !m_Task.isCanceled();
|
||
106 | |||
107 | } |
||
108 | |||
109 | |||
110 | private void addRegressionInfo() { |
||
111 | |||
112 | final DecimalFormat df = new DecimalFormat("####.###"); |
||
113 | final HTMLDoc doc = new HTMLDoc(); |
||
114 | doc.open(Sextante.getText("Regression"));
|
||
115 | doc.addHeader(Sextante.getText("Regression"), 2); |
||
116 | doc.startUnorderedList(); |
||
117 | doc.addListElement(m_Regression.getExpression()); |
||
118 | doc.addListElement("R2 = " + df.format(m_Regression.getR2()));
|
||
119 | doc.closeUnorderedList(); |
||
120 | doc.close(); |
||
121 | |||
122 | addOutputText(REGRESSION_DATA, Sextante.getText("Regression_values"), doc.getHTMLCode());
|
||
123 | |||
124 | } |
||
125 | |||
126 | |||
127 | private void calculateResiduals() throws IteratorException { |
||
128 | |||
129 | double dValue;
|
||
130 | double dGridValue;
|
||
131 | final Object value[] = new Object[5]; |
||
132 | final AnalysisExtent extent = m_Result.getWindowGridExtent();
|
||
133 | GridCell cell; |
||
134 | final double v = 100. / m_Regression.getYVar(); |
||
135 | |||
136 | final IFeatureIterator iter = m_Points.iterator();
|
||
137 | while (iter.hasNext()) {
|
||
138 | final IFeature feature = iter.next();
|
||
139 | final Geometry geom = feature.getGeometry();
|
||
140 | final Coordinate pt = geom.getCoordinate();
|
||
141 | dValue = Double.parseDouble(feature.getRecord().getValue(m_iField).toString());
|
||
142 | cell = extent.getGridCoordsFromWorldCoords(pt.x, pt.y); |
||
143 | dGridValue = m_Result.getCellValueAsDouble(cell.getX(), cell.getY()); |
||
144 | if (!m_Result.isNoDataValue(dGridValue)) {
|
||
145 | value[0] = new Double(dValue); |
||
146 | value[1] = new Double(dValue = m_Window.getValueAt(pt.x, pt.y)); |
||
147 | value[2] = new Double(dValue = m_Regression.getY(dValue)); |
||
148 | value[3] = new Double(dValue = dValue - ((Double) value[0]).doubleValue()); |
||
149 | value[4] = new Double(dValue * v); |
||
150 | m_Residuals.addFeature(geom, value); |
||
151 | } |
||
152 | } |
||
153 | iter.close(); |
||
154 | |||
155 | } |
||
156 | |||
157 | |||
158 | private void calculateResultingGrid() { |
||
159 | |||
160 | int x, y;
|
||
161 | int iNX, iNY;
|
||
162 | double dValue;
|
||
163 | |||
164 | iNX = m_Window.getNX(); |
||
165 | iNY = m_Window.getNY(); |
||
166 | |||
167 | for (y = 0; y < iNY; y++) { |
||
168 | for (x = 0; x < iNX; x++) { |
||
169 | dValue = m_Window.getCellValueAsDouble(x, y); |
||
170 | if (m_Window.isNoDataValue(dValue)) {
|
||
171 | m_Result.setNoData(x, y); |
||
172 | } |
||
173 | else {
|
||
174 | m_Result.setCellValue(x, y, m_Regression.getY(dValue)); |
||
175 | } |
||
176 | } |
||
177 | } |
||
178 | |||
179 | } |
||
180 | |||
181 | |||
182 | private void calculateRegression() throws GeoAlgorithmExecutionException { |
||
183 | |||
184 | double dValue, dGridValue;
|
||
185 | m_Regression = new Regression();
|
||
186 | int iType = 1; |
||
187 | |||
188 | try {
|
||
189 | iType = m_Parameters.getParameterValueAsInt(METHOD) + 1;
|
||
190 | } |
||
191 | catch (final Exception e) {} |
||
192 | |||
193 | final IFeatureIterator iter = m_Points.iterator();
|
||
194 | while (iter.hasNext()) {
|
||
195 | final IFeature feature = iter.next();
|
||
196 | final Geometry geom = feature.getGeometry();
|
||
197 | final Coordinate pt = geom.getCoordinate();
|
||
198 | dGridValue = m_Window.getValueAt(pt.x, pt.y); |
||
199 | if (!m_Window.isNoDataValue(dGridValue)) {
|
||
200 | try {
|
||
201 | dValue = Double.parseDouble(feature.getRecord().getValue(m_iField).toString());
|
||
202 | m_Regression.addValue(dGridValue, dValue); |
||
203 | } |
||
204 | catch (final NumberFormatException e) {} |
||
205 | } |
||
206 | } |
||
207 | iter.close(); |
||
208 | boolean bReturn = m_Regression.calculate(iType);
|
||
209 | if (!bReturn) {
|
||
210 | throw new GeoAlgorithmExecutionException(Sextante.getText("Could_not_calculate_regression")); |
||
211 | } |
||
212 | |||
213 | } |
||
214 | |||
215 | } |