CSVRecord.toList() does not give write access to the new List

This commit is contained in:
Gary Gregory 2022-08-10 05:51:53 -04:00
parent 532e08c3c4
commit e2c2fd40a5
3 changed files with 46 additions and 7 deletions

View File

@ -46,6 +46,7 @@
<action issue="CSV-269" type="fix" dev="ggregory" due-to="Auke te Winkel, Gary Gregory">CSVRecord.get(Enum) should use Enum.name() instead of Enum.toString().</action> <action issue="CSV-269" type="fix" dev="ggregory" due-to="Auke te Winkel, Gary Gregory">CSVRecord.get(Enum) should use Enum.name() instead of Enum.toString().</action>
<action type="fix" dev="ggregory" due-to="Gary Gregory">Allow org.apache.commons.csv.IOUtils.copy(Reader, Appendable, CharBuffer) to compile on Java 11 and run on Java 8.</action> <action type="fix" dev="ggregory" due-to="Gary Gregory">Allow org.apache.commons.csv.IOUtils.copy(Reader, Appendable, CharBuffer) to compile on Java 11 and run on Java 8.</action>
<action type="fix" dev="ggregory" due-to="Gary Gregory">Bump commons-parent from 52 to 53.</action> <action type="fix" dev="ggregory" due-to="Gary Gregory">Bump commons-parent from 52 to 53.</action>
<action issue="CSV-300" type="fix" dev="ggregory" due-to="Markus Spann, Gary Gregory">CSVRecord.get(Enum) should use Enum.name() instead of Enum.toString().</action>
<!-- ADD --> <!-- ADD -->
<action issue="CSV-291" type="add" dev="ggregory" due-to="Gary Gregory">Make CSVRecord#values() public.</action> <action issue="CSV-291" type="add" dev="ggregory" due-to="Gary Gregory">Make CSVRecord#values() public.</action>
<action issue="CSV-264" type="add" dev="ggregory" due-to="Sagar Tiwari, Seth Falco, Alex Herbert, Gary Gregory">Add DuplicateHeaderMode for flexibility with header strictness. #114.</action> <action issue="CSV-264" type="add" dev="ggregory" due-to="Sagar Tiwari, Seth Falco, Alex Herbert, Gary Gregory">Add DuplicateHeaderMode for flexibility with header strictness. #114.</action>

View File

@ -18,6 +18,7 @@
package org.apache.commons.csv; package org.apache.commons.csv;
import java.io.Serializable; import java.io.Serializable;
import java.util.ArrayList;
import java.util.Arrays; import java.util.Arrays;
import java.util.Iterator; import java.util.Iterator;
import java.util.LinkedHashMap; import java.util.LinkedHashMap;
@ -298,17 +299,26 @@ public final class CSVRecord implements Serializable, Iterable<String> {
} }
/** /**
* Converts the values to a List. * Converts the values to a new List.
* <p>
* Editing the list does not update this instance.
* </p>
* *
* @return a new List * @return a new List
* @since 1.9.0 * @since 1.9.0
*/ */
public List<String> toList() { public List<String> toList() {
return Arrays.asList(values); // Only allocate a single list of known size
final ArrayList<String> list = new ArrayList<>(values.length);
Stream.of(values).forEach(list::add);
return list;
} }
/** /**
* Copies this record into a new Map of header name to record value. * Copies this record into a new Map of header name to record value.
* <p>
* Editing the map does not update this instance.
* </p>
* *
* @return A new Map. The map is empty if the record has no headers. * @return A new Map. The map is empty if the record has no headers.
*/ */

View File

@ -16,6 +16,7 @@
*/ */
package org.apache.commons.csv; package org.apache.commons.csv;
import static org.junit.jupiter.api.Assertions.assertArrayEquals;
import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse; import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertNotNull;
@ -30,6 +31,7 @@ import java.io.ObjectInputStream;
import java.io.ObjectOutputStream; import java.io.ObjectOutputStream;
import java.io.StringReader; import java.io.StringReader;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.TreeMap; import java.util.TreeMap;
import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentHashMap;
@ -47,9 +49,7 @@ public class CSVRecordTest {
/** This enum overrides toString() but it's the names that matter. */ /** This enum overrides toString() but it's the names that matter. */
public enum EnumHeader { public enum EnumHeader {
FIRST("first"), FIRST("first"), SECOND("second"), THIRD("third");
SECOND("second"),
THIRD("third");
private final String number; private final String number;
@ -69,7 +69,7 @@ public class CSVRecordTest {
@BeforeEach @BeforeEach
public void setUp() throws Exception { public void setUp() throws Exception {
values = new String[] {"A", "B", "C"}; values = new String[] { "A", "B", "C" };
final String rowData = StringUtils.join(values, ','); final String rowData = StringUtils.join(values, ',');
try (final CSVParser parser = CSVFormat.DEFAULT.parse(new StringReader(rowData))) { try (final CSVParser parser = CSVFormat.DEFAULT.parse(new StringReader(rowData))) {
record = parser.iterator().next(); record = parser.iterator().next();
@ -273,7 +273,17 @@ public class CSVRecordTest {
} }
@Test @Test
public void testToList() { public void testToListAdd() {
String[] expected = values.clone();
final List<String> list = record.toList();
list.add("Last");
assertEquals("Last", list.get(list.size() - 1));
assertEquals(list.size(), values.length + 1);
assertArrayEquals(expected, values);
}
@Test
public void testToListFor() {
int i = 0; int i = 0;
for (final String value : record.toList()) { for (final String value : record.toList()) {
assertEquals(values[i], value); assertEquals(values[i], value);
@ -281,6 +291,24 @@ public class CSVRecordTest {
} }
} }
@Test
public void testToListForEach() {
AtomicInteger i = new AtomicInteger();
record.toList().forEach(e -> {
assertEquals(values[i.getAndIncrement()], e);
});
}
@Test
public void testToListSet() {
String[] expected = values.clone();
final List<String> list = record.toList();
list.set(list.size() - 1, "Last");
assertEquals("Last", list.get(list.size() - 1));
assertEquals(list.size(), values.length);
assertArrayEquals(expected, values);
}
@Test @Test
public void testToMap() { public void testToMap() {
final Map<String, String> map = this.recordWithHeader.toMap(); final Map<String, String> map = this.recordWithHeader.toMap();