3 回答
TA贡献1811条经验 获得超6个赞
我将分两步解决这个问题:首先,阅读标题,然后阅读其余的行:
static String[] headers(String path) throws IOException {
try (BufferedReader br = new BufferedReader(new FileReader(path))) {
return br.readLine().split(",");
}
}
现在,您可以使用上述方法如下:
String path = "sample.csv";
// Read headers
String[] headers = headers(path);
List<Map<String, String>> result = null;
// Read data
try (Stream<String> stream = Files.lines(Paths.get(path))) {
result = stream
.skip(1) // skip headers
.map(line -> line.split(","))
.map(data -> {
Map<String, String> map = new HashMap<>();
for (int i = 0; i < data.length; i++) {
map.put(headers[i], data[i]);
}
return map;
})
.collect(Collectors.toList());
}
您可以for在第二个map操作中更改循环:
try (Stream<String> stream = Files.lines(Paths.get(path))) {
result = stream
.skip(1) // skip headers
.map(line -> line.split(","))
.map(data -> IntStream.range(0, data.length)
.boxed()
.collect(Collectors.toMap(i -> headers[i], i -> data[i])))
.collect(Collectors.toList());
}
编辑:如果不是收集到列表,而是要对从每一行读取的地图执行操作,您可以按如下方式进行:
try (Stream<String> stream = Files.lines(Paths.get(path))) {
stream
.skip(1) // skip headers
.map(line -> line.split(","))
.map(data -> IntStream.range(0, data.length)
.boxed()
.collect(Collectors.toMap(i -> headers[i], i -> data[i])))
.forEach(System.out::println);
}
(这里的动作是打印每张地图)。
这个版本可以改进,即它装箱ints的流,然后int再次拆箱以将其用作headers和data数组的索引。此外,可以通过将每个映射的创建提取到私有方法来提高可读性。
注意:也许读取文件两次不是性能方面的最佳方法,但代码简单且富有表现力。除此之外,null处理、数据转换(即到数字或日期等)和边界情况(即没有标题、没有数据行或数据数组的不同长度等)留给读者作为练习;)
TA贡献1772条经验 获得超5个赞
我认为这就是你想要做的
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
import java.util.stream.Stream;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
public class App {
public static void main(String[] args) throws JsonProcessingException, IOException {
Stream<String> stream = Files.lines(Paths.get("src/main/resources/test1.csv"));
List<Map<String, Object>> readall = stream.map(l -> {
Map<String, Object> map = new HashMap<String, Object>();
String[] values = l.split(",");
map.put("name", values[0]);
map.put("age", values[1]);
return map;
}).collect(Collectors.toList());
ObjectMapper mapperObj = new ObjectMapper();
String jsonResp = mapperObj.writeValueAsString(readall);
System.out.println(jsonResp);
}
}
与 Java -8 Streams 一起使用,带有标头,并使用 jackson 将其转换为 json。使用过的 CSV
abc,20
bbc,30
TA贡献1890条经验 获得超9个赞
很简单,不要把它转换成字符串列表。将其转换为 HashMap 列表,然后使用 org.json 库将其转换为 json 。使用 jackson 将 CSV 转换为 Hashmap
让输入流为
InputStream stream = new FileInputStream(new File("filename.csv"));
示例:将 CSV 转换为 HashMap
public List<Map<String, Object>> read(InputStream stream) throws JsonProcessingException, IOException {
List<Map<String, Object>> response = new LinkedList<Map<String, Object>>();
CsvMapper mapper = new CsvMapper();
CsvSchema schema = CsvSchema.emptySchema().withHeader();
MappingIterator<Map<String, String>> iterator = mapper.reader(Map.class).with(schema).readValues(stream);
while (iterator.hasNext())
{
response.add(Collections.<String, Object>unmodifiableMap(iterator.next()));
}
return response;
}
将地图列表转换为 Json
JSONArray jsonArray = new JSONArray(response);
System.out.println(jsonArray.toString());
添加回答
举报