Revize 9e9e8d67
Přidáno uživatelem Michal Linha před asi 4 roky(ů)
src/main/java/vldc/aswi/utils/Converter.java | ||
---|---|---|
7 | 7 |
import vldc.aswi.model.table.contingencyTable.ContingencyTableRow; |
8 | 8 |
import vldc.aswi.model.table.contingencyTable.ContingencyTableRowCell; |
9 | 9 |
|
10 |
import javax.persistence.criteria.CriteriaBuilder; |
|
10 | 11 |
import java.util.ArrayList; |
11 | 12 |
import java.util.List; |
12 | 13 |
import java.util.Map; |
14 |
import java.util.concurrent.TimeUnit; |
|
13 | 15 |
|
14 | 16 |
/** |
15 | 17 |
* Class for converting classes. |
... | ... | |
27 | 29 |
public List<ContingencyTableRow> convertTableColumnsToContingencyTableRows(Map<String, TableColumn> tableColumns, |
28 | 30 |
List<NameUserName> rowNames, |
29 | 31 |
List<NameUserName> columnNames, |
30 |
List<ValueFunction> valueFunctions) {
|
|
31 |
/*
|
|
32 |
List<ValueFunction> valueFunctions) { |
|
33 |
long startTime = System.nanoTime();
|
|
32 | 34 |
List<ContingencyTableRow> contingencyTableRows = new ArrayList<>(); |
33 | 35 |
|
34 |
// Create header row with column names. |
|
35 |
ContingencyTableRow contingencyTableRowHeader = new ContingencyTableRow(true, 0); |
|
36 |
for (String columnName : tableColumns.keySet()) { |
|
37 |
contingencyTableRowHeader.addTableRowCell(new ContingencyTableRowCell(columnName, 0)); |
|
38 |
} |
|
39 |
contingencyTableRows.add(contingencyTableRowHeader); |
|
40 |
|
|
41 |
boolean listExpanded = false; |
|
36 |
long startTime2 = System.nanoTime(); |
|
37 |
List<ContingencyTableRow> headerRows = createHeaderOnlyRows(tableColumns, columnNames, valueFunctions); |
|
38 |
long stopTime2 = System.nanoTime(); |
|
39 |
System.out.println("Headers:" + TimeUnit.MILLISECONDS.convert((stopTime2 - startTime2), TimeUnit.NANOSECONDS)); |
|
42 | 40 |
|
43 |
// Create contingency table row. |
|
44 |
for (TableColumn tableColumn : tableColumns.values()) { |
|
45 |
List<String> values = tableColumn.getValues(); |
|
46 |
|
|
47 |
// If list is not created, then create it. |
|
48 |
if (!listExpanded) { |
|
49 |
for (int j = 0; j < values.size(); j++) { |
|
50 |
ContingencyTableRow contingencyTableRow = new ContingencyTableRow(false, 0); |
|
51 |
contingencyTableRows.add(contingencyTableRow); |
|
52 |
} |
|
53 |
listExpanded = true; |
|
54 |
} |
|
55 |
|
|
56 |
// Iterate through all values and assign one value per one row. |
|
57 |
for (int j = 0; j < values.size(); j++) { |
|
58 |
ContingencyTableRowCell contingencyTableRowCell = new ContingencyTableRowCell(values.get(j), 0); |
|
59 |
contingencyTableRows.get(j + 1).addTableRowCell(contingencyTableRowCell); |
|
60 |
} |
|
61 |
} |
|
62 |
|
|
63 |
*/ |
|
64 |
List<ContingencyTableRow> contingencyTableRows = new ArrayList<>(); |
|
65 |
|
|
66 |
List<ContingencyTableRow> headerRows = createHeaderOnlyRows(tableColumns, columnNames); |
|
41 |
long startTime3 = System.nanoTime(); |
|
67 | 42 |
List<ContingencyTableRow> dataRows = createDataRows(tableColumns, columnNames, rowNames, valueFunctions); |
43 |
long stopTime3 = System.nanoTime(); |
|
44 |
System.out.println("Rows:" + TimeUnit.MILLISECONDS.convert((stopTime3 - startTime3), TimeUnit.NANOSECONDS)); |
|
68 | 45 |
|
69 | 46 |
contingencyTableRows.addAll(headerRows); |
70 | 47 |
contingencyTableRows.addAll(dataRows); |
71 | 48 |
|
49 |
long stopTime = System.nanoTime(); |
|
50 |
System.out.println("Converter:" + TimeUnit.SECONDS.convert((stopTime - startTime), TimeUnit.NANOSECONDS) + "s"); |
|
51 |
|
|
72 | 52 |
return contingencyTableRows; |
73 | 53 |
} |
74 | 54 |
|
75 |
private List<ContingencyTableRow> createHeaderOnlyRows(Map<String, TableColumn> tableColumns, List<NameUserName> columnNames) { |
|
55 |
/** |
|
56 |
* Generates header rows. |
|
57 |
* @param tableColumns Map of TableColumn |
|
58 |
* @param columnNames list of column and user column names |
|
59 |
* @param valueFunctions list of values and their functions |
|
60 |
* @return list of contingency table rows |
|
61 |
*/ |
|
62 |
private List<ContingencyTableRow> createHeaderOnlyRows(Map<String, TableColumn> tableColumns, |
|
63 |
List<NameUserName> columnNames, List<ValueFunction> valueFunctions) { |
|
76 | 64 |
List<List<String>> values = new ArrayList<>(); |
77 | 65 |
columnNodes = new ArrayList<>(); |
78 | 66 |
List<ContingencyTableRow> headerRows = new ArrayList<>(); |
67 |
|
|
68 |
List<String> valueOptions = new ArrayList<>(); |
|
69 |
for (ValueFunction valueFunction : valueFunctions) { |
|
70 |
valueOptions.add(valueFunction.getFunction() + " z " + valueFunction.getValue()); |
|
71 |
} |
|
72 |
values.add(valueOptions); |
|
73 |
headerRows.add(new ContingencyTableRow(true, 0)); |
|
74 |
|
|
79 | 75 |
for(NameUserName nameUserName : columnNames) { |
80 | 76 |
TableColumn column = tableColumns.get(nameUserName.getName()); |
81 | 77 |
values.add(getOriginalValuesFromList(column.getValues())); |
82 | 78 |
headerRows.add(new ContingencyTableRow(true, 0)); |
83 | 79 |
} |
84 | 80 |
|
85 |
Node node = new Node(); |
|
86 |
generateColumns(0, values, columnNodes, node); |
|
87 |
|
|
88 | 81 |
for (int i = 0; i < values.size(); i++) { |
89 | 82 |
int colSpan = 1; |
90 | 83 |
for (int j = values.size() - 1; j > i; j--) { |
... | ... | |
103 | 96 |
for (int k = 0; k < loopCount; k++) { |
104 | 97 |
for (String value : values.get(i)) { |
105 | 98 |
headerRows.get(i).addTableRowCell(new ContingencyTableRowCell(value, colSpan)); |
106 |
if (i != values.size() - 1) { |
|
99 |
if (i != values.size() - 1 && i != 0) {
|
|
107 | 100 |
headerRows.get(i).addTableRowCell(new ContingencyTableRowCell(value + " Celkem", 1)); |
108 | 101 |
} |
109 | 102 |
} |
110 | 103 |
|
111 |
for (int l = 0; l < i; l++) { |
|
104 |
for (int l = 0; l < i - 1; l++) {
|
|
112 | 105 |
headerRows.get(i).addTableRowCell(new ContingencyTableRowCell("", 1)); |
113 | 106 |
} |
114 | 107 |
} |
115 |
if (i == 0) { |
|
116 |
headerRows.get(i).addTableRowCell(new ContingencyTableRowCell("Celkový počet", 1)); |
|
117 |
} |
|
118 |
else { |
|
119 |
headerRows.get(i).addTableRowCell(new ContingencyTableRowCell("", 1)); |
|
108 |
for(ValueFunction valueFunction: valueFunctions) { |
|
109 |
if (i == 0) { |
|
110 |
headerRows.get(i).addTableRowCell(new ContingencyTableRowCell("Celkový " + valueFunction.getFunction() + |
|
111 |
" z " + valueFunction.getValue(), 1)); |
|
112 |
} else { |
|
113 |
headerRows.get(i).addTableRowCell(new ContingencyTableRowCell("", 1)); |
|
114 |
} |
|
120 | 115 |
} |
121 | 116 |
} |
122 | 117 |
|
118 |
long startTime = System.nanoTime(); |
|
119 |
values.remove(0); |
|
120 |
Node node = new Node(); |
|
121 |
generateColumns(0, values, columnNodes, node); |
|
122 |
long stopTime = System.nanoTime(); |
|
123 |
System.out.println("Colums list:" + TimeUnit.MILLISECONDS.convert((stopTime - startTime), TimeUnit.NANOSECONDS)); |
|
124 |
|
|
123 | 125 |
return headerRows; |
124 | 126 |
} |
125 | 127 |
|
128 |
/** |
|
129 |
* Gets original values of a given list. |
|
130 |
* @param list list from which original values should be taken |
|
131 |
* @return list of original values |
|
132 |
*/ |
|
126 | 133 |
private List<String> getOriginalValuesFromList(List<String> list) { |
127 | 134 |
List<String> origList = new ArrayList<>(); |
128 | 135 |
|
... | ... | |
135 | 142 |
return origList; |
136 | 143 |
} |
137 | 144 |
|
145 |
/** |
|
146 |
* Creates data rows. |
|
147 |
* @param tableColumns Map of TableColumn |
|
148 |
* @param columnNames list of column and user column names |
|
149 |
* @param rowNames list of row and user row names |
|
150 |
* @param valueFunctions list of values and their functions |
|
151 |
* @return list of contingency table rows |
|
152 |
*/ |
|
138 | 153 |
private List<ContingencyTableRow> createDataRows(Map<String, TableColumn> tableColumns, List<NameUserName> columnNames, |
139 | 154 |
List<NameUserName> rowNames, List<ValueFunction> valueFunctions) { |
140 | 155 |
List<ContingencyTableRow> dataRows = new ArrayList<>(); |
... | ... | |
145 | 160 |
values.add(getOriginalValuesFromList(column.getValues())); |
146 | 161 |
} |
147 | 162 |
|
163 |
long startTime = System.nanoTime(); |
|
148 | 164 |
Node node = new Node(); |
149 | 165 |
generateRows(dataRows, 0, values, rowNodes, node); |
166 |
long stopTime = System.nanoTime(); |
|
167 |
System.out.println("Rows List:" + TimeUnit.MILLISECONDS.convert((stopTime - startTime), TimeUnit.NANOSECONDS)); |
|
150 | 168 |
|
151 | 169 |
for (int i = 0; i < dataRows.size(); i++) { |
152 |
fillRowWithCountData(dataRows.get(i), tableColumns, rowNodes.get(i), rowNames, columnNames, valueFunctions);
|
|
170 |
fillRowWithData(dataRows.get(i), tableColumns, rowNodes.get(i), rowNames, columnNames, valueFunctions); |
|
153 | 171 |
} |
154 | 172 |
|
155 | 173 |
return dataRows; |
156 | 174 |
} |
157 | 175 |
|
176 |
/** |
|
177 |
* Recursively generates all possible row combinations, sorted as in contingency table. |
|
178 |
* @param rows list of sorted contingency table rows |
|
179 |
* @param index index in the values list |
|
180 |
* @param values list of lists of values of each query row |
|
181 |
* @param rowNodes list of row nodes |
|
182 |
* @param prevNode parent node of the nodes |
|
183 |
*/ |
|
158 | 184 |
private void generateRows(List<ContingencyTableRow> rows, int index, List<List<String>> values, List<Node> rowNodes, |
159 | 185 |
Node prevNode) { |
160 | 186 |
if (index < values.size()) { |
... | ... | |
177 | 203 |
} |
178 | 204 |
} |
179 | 205 |
|
206 |
/** |
|
207 |
* Recursively generates all possible column combinations, sorted as in contingency table. |
|
208 |
* @param index index in the values list |
|
209 |
* @param values list of lists of values of each query row |
|
210 |
* @param columnNodes list of column nodes |
|
211 |
* @param prevNode parent node of the nodes |
|
212 |
*/ |
|
180 | 213 |
private void generateColumns(int index, List<List<String>> values, List<Node> columnNodes, Node prevNode) { |
181 | 214 |
if (index < values.size()) { |
182 | 215 |
List<String> list = values.get(index); |
... | ... | |
190 | 223 |
} |
191 | 224 |
} |
192 | 225 |
|
193 |
private void fillRowWithCountData(ContingencyTableRow row, Map<String, TableColumn> tableColumns, Node node, |
|
194 |
List<NameUserName> rowNames, List<NameUserName> columnNames, List<ValueFunction> valueFunctions) { |
|
195 |
int totalCount = 0; |
|
196 |
//sloupec v kont. tabulce |
|
197 |
for (Node columnNode : columnNodes) { |
|
198 |
int count = 0; |
|
199 |
// radek v orig. tabulce |
|
200 |
for (int i = 0; i < tableColumns.get(rowNames.get(0).getName()).getValues().size(); i++) { |
|
201 |
boolean isUsable = true; |
|
202 |
//zvoleny sloupec z radku |
|
203 |
for (int j = 0; j < node.getValues().size(); j++) { |
|
204 |
if (!tableColumns.get(rowNames.get(j).getName()).getValues().get(i).equals(node.getValues().get(j))) { |
|
205 |
isUsable = false; |
|
206 |
break; |
|
207 |
} |
|
208 |
} |
|
209 |
int j; |
|
210 |
// zvoleny sloupec ze sloupcu |
|
211 |
for (j = 0; j < columnNode.getValues().size(); j++) { |
|
212 |
if (!tableColumns.get(columnNames.get(j).getName()).getValues().get(i).equals(columnNode.getValues().get(j))) { |
|
213 |
isUsable = false; |
|
214 |
break; |
|
226 |
/** |
|
227 |
* Fills each data row with data. |
|
228 |
* @param row row to ne filled with data |
|
229 |
* @param tableColumns Map of TableColumn |
|
230 |
* @param node node of the row |
|
231 |
* @param rowNames list of row names and user names |
|
232 |
* @param columnNames list of column names and user names |
|
233 |
* @param valueFunctions list of values and their functions |
|
234 |
*/ |
|
235 |
private void fillRowWithData(ContingencyTableRow row, Map<String, TableColumn> tableColumns, Node node, |
|
236 |
List<NameUserName> rowNames, List<NameUserName> columnNames, List<ValueFunction> valueFunctions) { |
|
237 |
if (columnNodes.size() == 0) { |
|
238 |
columnNodes.add(new Node()); |
|
239 |
} |
|
240 |
|
|
241 |
List<Integer> usableIDs = getUsableIDs(tableColumns, node, rowNames); |
|
242 |
|
|
243 |
int[] totals = new int[valueFunctions.size()]; |
|
244 |
//hodnota |
|
245 |
for (int v = 0; v < valueFunctions.size(); v++) { |
|
246 |
ValueFunction valueFunction = valueFunctions.get(v); |
|
247 |
//sloupec v kont. tabulce |
|
248 |
for (Node columnNode : columnNodes) { |
|
249 |
int result = 0; |
|
250 |
// radek v orig. tabulce |
|
251 |
for (Integer usableID : usableIDs) { |
|
252 |
boolean isUsable = true; |
|
253 |
int j; |
|
254 |
// zvoleny sloupec ze sloupcu |
|
255 |
for (j = 0; j < columnNode.getValues().size(); j++) { |
|
256 |
if (!tableColumns.get(columnNames.get(j).getName()).getValues().get(usableID).equals(columnNode.getValues().get(j))) { |
|
257 |
isUsable = false; |
|
258 |
break; |
|
259 |
} |
|
215 | 260 |
} |
216 |
} |
|
217 |
// zvoleny sloupec z hodnot |
|
218 |
for (ValueFunction valueFunction : valueFunctions) { |
|
219 |
if (tableColumns.get(valueFunction.getValue()).getValues().get(i) == null) { |
|
261 |
// zvoleny sloupec z hodnot |
|
262 |
if (tableColumns.get(valueFunction.getValue()).getValues().get(usableID) == null) { |
|
220 | 263 |
isUsable = false; |
221 |
break; |
|
222 | 264 |
} |
223 |
} |
|
224 | 265 |
|
225 |
if (isUsable) { |
|
226 |
count++; |
|
227 |
if (j - 1 == 0) { |
|
228 |
totalCount++; |
|
266 |
if (isUsable) { |
|
267 |
if (valueFunction.getFunction().equals("COUNT")) { |
|
268 |
result++; |
|
269 |
} else if (valueFunction.getFunction().equals("SUM")) { |
|
270 |
result += Integer.parseInt(tableColumns.get(valueFunction.getValue()).getValues().get(usableID)); |
|
271 |
} |
|
272 |
if (j - 1 == 0 || j == 0) { |
|
273 |
if (valueFunction.getFunction().equals("COUNT")) { |
|
274 |
totals[v]++; |
|
275 |
} else if (valueFunction.getFunction().equals("SUM")) { |
|
276 |
totals[v] += Integer.parseInt(tableColumns.get(valueFunction.getValue()).getValues().get(usableID)); |
|
277 |
} |
|
278 |
} |
|
229 | 279 |
} |
230 | 280 |
} |
281 |
row.addTableRowCell(new ContingencyTableRowCell(Integer.toString(result), 0)); |
|
231 | 282 |
} |
283 |
} |
|
284 |
for (int total : totals) { |
|
285 |
row.addTableRowCell(new ContingencyTableRowCell(Integer.toString(total), 0)); |
|
286 |
} |
|
287 |
} |
|
288 |
|
|
289 |
/** |
|
290 |
* Gets a list of IDs of the query rows that fit the contingency table row settings. |
|
291 |
* @param tableColumns Map of TableColumn |
|
292 |
* @param node node of the row |
|
293 |
* @param rowNames list of row names and user names |
|
294 |
* @return list of usable IDs |
|
295 |
*/ |
|
296 |
private List<Integer> getUsableIDs(Map<String, TableColumn> tableColumns, Node node, List<NameUserName> rowNames) { |
|
297 |
List<Integer> ids = new ArrayList<>(); |
|
232 | 298 |
|
233 |
row.addTableRowCell(new ContingencyTableRowCell(Integer.toString(count), 0)); |
|
299 |
for (int i = 0; i < tableColumns.get(rowNames.get(0).getName()).getValues().size(); i++) { |
|
300 |
for (int j = 0; j < node.getValues().size(); j++) { |
|
301 |
if (tableColumns.get(rowNames.get(j).getName()).getValues().get(i).equals(node.getValues().get(j))) { |
|
302 |
ids.add(i); |
|
303 |
} |
|
304 |
} |
|
234 | 305 |
} |
235 | 306 |
|
236 |
row.addTableRowCell(new ContingencyTableRowCell(Integer.toString(totalCount), 0));
|
|
307 |
return ids;
|
|
237 | 308 |
} |
238 | 309 |
} |
Také k dispozici: Unified diff
re #7885 added SUM and ability to work with multiple values and sorted parameters in configuration, optimization