Skip to content

Commit 80d3675

Browse files
committed
DefaultTableIOPlugin: apply style formatter
1 parent 0c12425 commit 80d3675

File tree

2 files changed

+175
-145
lines changed

2 files changed

+175
-145
lines changed

src/main/java/org/scijava/table/io/DefaultTableIOPlugin.java

Lines changed: 96 additions & 76 deletions
Original file line numberDiff line numberDiff line change
@@ -54,22 +54,24 @@
5454
import org.scijava.util.FileUtils;
5555

5656
/**
57-
* Plugin for reading/writing {@link GenericTable}s.
58-
*
57+
* Plugin for reading/writing {@link Table}s.
58+
*
5959
* @author Leon Yang
6060
*/
6161
@SuppressWarnings("rawtypes")
6262
@Plugin(type = TableIOPlugin.class, priority = Priority.LOW)
63-
public class DefaultTableIOPlugin extends AbstractIOPlugin<Table> implements TableIOPlugin {
63+
public class DefaultTableIOPlugin extends AbstractIOPlugin<Table> implements
64+
TableIOPlugin
65+
{
6466

6567
@Parameter
6668
private DataHandleService dataHandleService;
6769

6870
// FIXME: The "txt" extension is extremely general and will conflict with
6971
// other plugins. Consider another way to check supportsOpen/Close.
70-
private static final Set<String> SUPPORTED_EXTENSIONS = Collections
71-
.unmodifiableSet(new HashSet<>(Arrays.asList("csv", "txt", "prn", "dif",
72-
"rtf")));
72+
private static final Set<String> SUPPORTED_EXTENSIONS = //
73+
Collections.unmodifiableSet(new HashSet<>(//
74+
Arrays.asList("csv", "txt", "prn", "dif", "rtf")));
7375

7476
@Override
7577
public boolean supportsOpen(final Location source) {
@@ -84,8 +86,9 @@ public boolean supportsOpen(final String source) {
8486
}
8587

8688
@Override
87-
public boolean supportsSave(Object data, String destination) {
88-
return supports(destination) && Table.class.isAssignableFrom(data.getClass());
89+
public boolean supportsSave(final Object data, final String destination) {
90+
return supports(destination) && //
91+
Table.class.isAssignableFrom(data.getClass());
8992
}
9093

9194
@Override
@@ -101,7 +104,9 @@ public boolean supportsSave(final String source) {
101104
/**
102105
* Process a given line into a list of tokens.
103106
*/
104-
private ArrayList<String> processRow(final String line, char separator, char quote) throws IOException {
107+
private ArrayList<String> processRow(final String line, final char separator,
108+
final char quote) throws IOException
109+
{
105110
final ArrayList<String> row = new ArrayList<>();
106111
final StringBuilder sb = new StringBuilder();
107112
int idx = 0;
@@ -154,11 +159,15 @@ else if (line.charAt(idx) == separator) {
154159
}
155160

156161
@Override
157-
public GenericTable open(final Location source, TableIOOptions options) throws IOException {
162+
public GenericTable open(final Location source, final TableIOOptions options)
163+
throws IOException
164+
{
158165
return open(source, options.values);
159166
}
160167

161-
private GenericTable open(final Location source, TableIOOptions.Values options) throws IOException {
168+
private GenericTable open(final Location source,
169+
final TableIOOptions.Values options) throws IOException
170+
{
162171

163172
final GenericTable table = new DefaultGenericTable();
164173

@@ -168,7 +177,7 @@ private GenericTable open(final Location source, TableIOOptions.Values options)
168177
if (!handle.exists()) {
169178
throw new IOException("Cannot open source");
170179
}
171-
long length = handle.length();
180+
final long length = handle.length();
172181

173182
final byte[] buffer = new byte[(int) length];
174183
handle.read(buffer);
@@ -177,14 +186,14 @@ private GenericTable open(final Location source, TableIOOptions.Values options)
177186

178187
final char separator = options.columnDelimiter();
179188
final char quote = options.quote();
180-
boolean readRowHeaders = options.readRowHeaders();
181-
boolean readColHeaders = options.readColumnHeaders();
189+
final boolean readRowHeaders = options.readRowHeaders();
190+
final boolean readColHeaders = options.readColumnHeaders();
182191

183192
// split by any line delimiter
184193
final String[] lines = text.split("\\R");
185194
if (lines.length == 0) return table;
186195
// process first line to get number of cols
187-
Map<Integer, Function<String, ?>> columnParsers = new HashMap<>();
196+
final Map<Integer, Function<String, ?>> columnParsers = new HashMap<>();
188197
{
189198
final ArrayList<String> tokens = processRow(lines[0], separator, quote);
190199
if (readColHeaders) {
@@ -207,7 +216,8 @@ private GenericTable open(final Location source, TableIOOptions.Values options)
207216
table.appendRow();
208217
}
209218
for (int i = 0; i < cols.size(); i++) {
210-
Function<String, ?> parser = getParser(cols.get(i), i, options);
219+
final Function<String, ?> parser = getParser(cols.get(i), i,
220+
options);
211221
columnParsers.put(i, parser);
212222
table.set(i, 0, parser.apply(cols.get(i)));
213223
}
@@ -230,7 +240,7 @@ private GenericTable open(final Location source, TableIOOptions.Values options)
230240
" is not the same length as the first line.");
231241
}
232242
for (int i = 0; i < cols.size(); i++) {
233-
if(lineNum == 1 && readColHeaders) {
243+
if (lineNum == 1 && readColHeaders) {
234244
columnParsers.put(i, getParser(cols.get(i), i, options));
235245
}
236246
table.set(i, lineNum - 1, columnParsers.get(i).apply(cols.get(i)));
@@ -240,36 +250,39 @@ private GenericTable open(final Location source, TableIOOptions.Values options)
240250
return table;
241251
}
242252

243-
private static Function<String, ?> getParser(String content, int column, TableIOOptions.Values options) {
244-
ColumnTableIOOptions.Values colOptions = options.column(column);
245-
if(colOptions != null) return colOptions.parser();
246-
if(options.guessParser()) return guessParser(content);
253+
private static Function<String, ?> getParser(final String content,
254+
final int column, final TableIOOptions.Values options)
255+
{
256+
final ColumnTableIOOptions.Values colOptions = options.column(column);
257+
if (colOptions != null) return colOptions.parser();
258+
if (options.guessParser()) return guessParser(content);
247259
return options.parser();
248260
}
249261

250-
static Function<String, ?> guessParser(String content) {
262+
static Function<String, ?> guessParser(final String content) {
251263
try {
252-
Function<String, ?> function = s -> Double.valueOf(s
253-
.replace("infinity", "Infinity")
254-
.replace("Nan", "NaN")
255-
);
264+
final Function<String, ?> function = s -> Double.valueOf(s.replace(
265+
"infinity", "Infinity").replace("Nan", "NaN"));
256266
function.apply(content);
257267
return function;
258-
} catch(NumberFormatException ignored) {}
259-
if(content.equalsIgnoreCase("true")||content.equalsIgnoreCase("false")) {
268+
}
269+
catch (final NumberFormatException ignored) {}
270+
if (content.equalsIgnoreCase("true") || content.equalsIgnoreCase("false")) {
260271
return Boolean::valueOf;
261272
}
262273
return String::valueOf;
263274
}
264275

265276
@Override
266-
public void save(final Table table, final Location destination, final TableIOOptions options)
267-
throws IOException {
277+
public void save(final Table table, final Location destination,
278+
final TableIOOptions options) throws IOException
279+
{
268280
save(table, destination, options.values);
269281
}
270282

271-
private void save(final Table table, final Location destination, final TableIOOptions.Values options)
272-
throws IOException {
283+
private void save(final Table table, final Location destination,
284+
final TableIOOptions.Values options) throws IOException
285+
{
273286

274287
try (final DataHandle<Location> handle = //
275288
dataHandleService.create(destination))
@@ -280,58 +293,63 @@ private void save(final Table table, final Location destination, final TableIOOp
280293
final String eol = options.rowDelimiter();
281294
final char quote = options.quote();
282295

283-
final StringBuilder sb = new StringBuilder();
284-
// write column headers
285-
if (writeCH) {
286-
if (writeRH) {
287-
sb.append(tryQuote(options.cornerText(), separator, quote));
288-
if (table.getColumnCount() > 0) {
289-
sb.append(separator);
290-
sb.append(tryQuote(table.getColumnHeader(0), separator, quote));
291-
}
292-
}
293-
// avoid adding extra separator when there is 0 column
294-
else if (table.getColumnCount() > 0) {
295-
sb.append(tryQuote(table.getColumnHeader(0), separator, quote));
296-
}
297-
for (int col = 1; col < table.getColumnCount(); col++) {
296+
final StringBuilder sb = new StringBuilder();
297+
// write column headers
298+
if (writeCH) {
299+
if (writeRH) {
300+
sb.append(tryQuote(options.cornerText(), separator, quote));
301+
if (table.getColumnCount() > 0) {
298302
sb.append(separator);
299-
sb.append(tryQuote(table.getColumnHeader(col), separator, quote));
303+
sb.append(tryQuote(table.getColumnHeader(0), separator, quote));
300304
}
301-
sb.append(eol);
302-
handle.writeBytes(sb.toString());
303-
sb.setLength(0);
304305
}
305-
// write each row
306-
for (int row = 0; row < table.getRowCount(); row++) {
307-
Function<Object, String> formatter = getFormatter(options, 0);
308-
if (writeRH) {
309-
sb.append(tryQuote(table.getRowHeader(row), separator, quote));
310-
if (table.getColumnCount() > 0) {
311-
sb.append(separator);
312-
sb.append(tryQuote(formatter.apply(table.get(0, row)), separator, quote));
313-
}
314-
}
315-
// avoid adding extra separator when there is 0 column
316-
else if (table.getColumnCount() > 0) {
317-
sb.append(tryQuote(formatter.apply(table.get(0, row)), separator, quote));
318-
}
319-
for (int col = 1; col < table.getColumnCount(); col++) {
320-
formatter = getFormatter(options, col);
306+
// avoid adding extra separator when there is 0 column
307+
else if (table.getColumnCount() > 0) {
308+
sb.append(tryQuote(table.getColumnHeader(0), separator, quote));
309+
}
310+
for (int col = 1; col < table.getColumnCount(); col++) {
311+
sb.append(separator);
312+
sb.append(tryQuote(table.getColumnHeader(col), separator, quote));
313+
}
314+
sb.append(eol);
315+
handle.writeBytes(sb.toString());
316+
sb.setLength(0);
317+
}
318+
// write each row
319+
for (int row = 0; row < table.getRowCount(); row++) {
320+
Function<Object, String> formatter = getFormatter(options, 0);
321+
if (writeRH) {
322+
sb.append(tryQuote(table.getRowHeader(row), separator, quote));
323+
if (table.getColumnCount() > 0) {
321324
sb.append(separator);
322-
sb.append(tryQuote(formatter.apply(table.get(col, row)), separator, quote));
325+
sb.append(tryQuote(formatter.apply(table.get(0, row)), separator,
326+
quote));
323327
}
324-
sb.append(eol);
325-
handle.writeBytes(sb.toString());
326-
sb.setLength(0);
327328
}
329+
// avoid adding extra separator when there is 0 column
330+
else if (table.getColumnCount() > 0) {
331+
sb.append(tryQuote(formatter.apply(table.get(0, row)), separator,
332+
quote));
333+
}
334+
for (int col = 1; col < table.getColumnCount(); col++) {
335+
formatter = getFormatter(options, col);
336+
sb.append(separator);
337+
sb.append(tryQuote(formatter.apply(table.get(col, row)), separator,
338+
quote));
339+
}
340+
sb.append(eol);
341+
handle.writeBytes(sb.toString());
342+
sb.setLength(0);
343+
}
328344
}
329345

330346
}
331347

332-
private Function<Object, String> getFormatter(TableIOOptions.Values options, int i) {
333-
ColumnTableIOOptions.Values columnOptions = options.column(i);
334-
if(columnOptions != null) return columnOptions.formatter();
348+
private Function<Object, String> getFormatter(
349+
final TableIOOptions.Values options, final int i)
350+
{
351+
final ColumnTableIOOptions.Values columnOptions = options.column(i);
352+
if (columnOptions != null) return columnOptions.formatter();
335353
return options.formatter();
336354
}
337355

@@ -340,11 +358,13 @@ private Function<Object, String> getFormatter(TableIOOptions.Values options, int
340358
* <li>it is null or empty</li>
341359
* <li>it has quotes inside</li>
342360
* <li>it has separators or EOL inside</li>
343-
*
361+
*
344362
* @param str string to quote
345363
* @return string, possibly quoted
346364
*/
347-
private String tryQuote(final String str, char separator, char quote) {
365+
private String tryQuote(final String str, final char separator,
366+
final char quote)
367+
{
348368
if (str == null || str.length() == 0) return "" + quote + quote;
349369
if (str.indexOf(quote) != -1) return quote + str.replace("" + quote, "" +
350370
quote + quote) + quote;

0 commit comments

Comments
 (0)