Преобразование файла CSV в объект JSON в Java - PullRequest
3 голосов
/ 02 марта 2012

Существует ли библиотека Java с открытым исходным кодом для преобразования файла CSV (или XLS) в объект JSON?

Я пытался использовать json.cdl , но почему-то это не похоже наработать для больших строк CSV.

Я пытаюсь найти что-то вроде http://www.cparker15.com/code/utilities/csv-to-json/,, но написано на Java.

Ответы [ 9 ]

4 голосов
/ 02 марта 2012

Вы можете использовать Open CSV для отображения CSV в Java Bean, а затем использовать JAXB для преобразования Java Bean в объект JSON.

http://opencsv.sourceforge.net/#javabean-integration

http://jaxb.java.net/guide/Mapping_your_favorite_class.html

3 голосов
/ 17 марта 2015

Вот моя Java-программа и надеюсь, что кто-нибудь найдет ее полезной.

Формат должен быть таким:

"SYMBOL, ДАТА, CLOSE_PRICE, OPEN_PRICE, HIGH_PRICE, LOW_PRICE, ТОМ, ADJ_CLOSE

AAIT, 2015-02-26 00: 00: 00.000, -35,152,0,35,152,35.12,679,0

AAL, 2015-02-26 00: 00: 00.000,49.35,50,38,50,38,49.02,7572135,0 "

Первая строка - заголовки столбцов. Кавычек нет нигде. Разделяйте запятыми, а не точками с запятой. Вы получаете сделку.

/* Summary: Converts a CSV file to a JSON file.*/

//import java.util.*;
import java.io.*;

import javax.swing.*;
import javax.swing.filechooser.FileNameExtensionFilter;

public class CSVtoJSON extends JFrame{
    private static final long serialVersionUID = 1L;
    private static File CSVFile;
    private static BufferedReader read;
    private static BufferedWriter write;

    public CSVtoJSON(){
        FileNameExtensionFilter filter = new FileNameExtensionFilter("comma separated values", "csv");
        JFileChooser choice = new JFileChooser();
        choice.setFileFilter(filter); //limit the files displayed

        int option = choice.showOpenDialog(this);
        if (option == JFileChooser.APPROVE_OPTION) {
            CSVFile = choice.getSelectedFile();
        }
        else{
            JOptionPane.showMessageDialog(this, "Did not select file. Program will exit.", "System Dialog", JOptionPane.PLAIN_MESSAGE);         
            System.exit(1);
        }
    }

    public static void main(String args[]){
        CSVtoJSON parse = new CSVtoJSON();
        parse.convert();

        System.exit(0);
    }

    private void convert(){
        /*Converts a .csv file to .json. Assumes first line is header with columns*/
        try {
            read = new BufferedReader(new FileReader(CSVFile));

            String outputName = CSVFile.toString().substring(0, 
                    CSVFile.toString().lastIndexOf(".")) + ".json"; 
            write = new BufferedWriter(new FileWriter(new File(outputName)));

            String line;
            String columns[]; //contains column names
            int num_cols;
            String tokens[];

            int progress = 0; //check progress

            //initialize columns
            line = read.readLine(); 
            columns = line.split(",");
            num_cols = columns.length;


            write.write("["); //begin file as array
            line = read.readLine();


            while(true) {
                tokens = line.split(",");

                if (tokens.length == num_cols){ //if number columns equal to number entries
                    write.write("{");

                    for (int k = 0; k < num_cols; ++k){ //for each column 
                        if (tokens[k].matches("^-?[0-9]*\\.?[0-9]*$")){ //if a number
                            write.write("\"" + columns[k] + "\": " + tokens[k]);
                            if (k < num_cols - 1) write.write(", ");                                                }
                        else { //if a string
                            write.write("\"" + columns[k] + "\": \"" + tokens[k] + "\"");
                            if (k < num_cols - 1) write.write(", ");
                        }
                    }

                    ++progress; //progress update
                    if (progress % 10000 == 0) System.out.println(progress); //print progress           


                    if((line = read.readLine()) != null){//if not last line
                        write.write("},");
                        write.newLine();
                    }
                    else{
                        write.write("}]");//if last line
                        write.newLine();
                        break;
                    }
                }
                else{
                    //line = read.readLine(); //read next line if wish to continue parsing despite error 
                    JOptionPane.showMessageDialog(this, "ERROR: Formatting error line " + (progress + 2)
                     + ". Failed to parse.", 
                            "System Dialog", JOptionPane.PLAIN_MESSAGE);                    
                    System.exit(-1); //error message
                }
            }

            JOptionPane.showMessageDialog(this, "File converted successfully to "     + outputName, 
                    "System Dialog", JOptionPane.PLAIN_MESSAGE);

            write.close();
            read.close();
        }
        catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }       
    }
    }

Требуется Swing, но поставляется с изящным небольшим графическим интерфейсом, поэтому те, кто не знает абсолютно Java, могут использовать его после упаковки в исполняемый файл .jar. Не стесняйтесь улучшать это. Спасибо StackOverflow за помощь мне все эти годы.

2 голосов
/ 15 августа 2013

@ Mouscellious в основном ответил на это для вас, поэтому, пожалуйста, дайте ему кредит.

Вот что я придумал:

package edu.apollogrp.csvtojson;

import au.com.bytecode.opencsv.bean.CsvToBean;
import au.com.bytecode.opencsv.bean.HeaderColumnNameMappingStrategy;
import org.codehaus.jackson.map.ObjectMapper;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.List;

public class ConvertCsvToJson {
    public static void main(String[] args) throws IOException, ClassNotFoundException {
        if (args.length > 1) {
            String pathToCsvFile = args[0];
            String javaBeanClassName = "edu.apollogrp.csvtojson.bean." + args[1];
            final File file = new File(pathToCsvFile);
            if (!file.exists()) {
                System.out.println("The file you specified does not exist. path=" + pathToCsvFile);
            }
            Class<?> type = null;
            try {
                type = Class.forName(javaBeanClassName);
            } catch (ClassNotFoundException e) {
                System.out.println("The java bean you specified does not exist. className=" + javaBeanClassName);
            }

            HeaderColumnNameMappingStrategy strat = new HeaderColumnNameMappingStrategy();
            strat.setType(type);

            CsvToBean csv = new CsvToBean();
            List list = csv.parse(strat, new InputStreamReader(new FileInputStream(file)));
            System.out.println(new ObjectMapper().writeValueAsString(list));
        } else {
            System.out.println("Please specify the path to the csv file.");
        }
    }
}

Я использовал maven для включения зависимостей, но вы также можете загрузить их вручную и включить в свой путь к классам.

<dependency>
    <groupId>net.sf.opencsv</groupId>
    <artifactId>opencsv</artifactId>
    <version>2.0</version>
</dependency>

<dependency>
    <groupId>org.codehaus.jackson</groupId>
    <artifactId>jackson-mapper-asl</artifactId>
    <version>1.9.12</version>
</dependency>
<dependency>
    <groupId>org.codehaus.jackson</groupId>
    <artifactId>jackson-core-asl</artifactId>
    <version>1.9.12</version>
</dependency>
2 голосов
/ 02 марта 2012

Если ваш CSV прост, тогда его легко написать вручную - но CSV может включать в себя неприятные крайние случаи с цитированием, пропущенными значениями и т. Д.

  • загрузить файл, используя BufferedReader.readLine()
  • используйте String.split(",") для получения значения из каждой строки - NB этот подход будет работать правильно, только если ваши значения не имеют запятых!
  • записать каждое значение в вывод, используя BufferedWriter
    • с необходимыми скобками JSON и цитированием

Возможно, вы захотите использовать библиотеку CSV, а затем конвертировать в JSON «вручную»

1 голос
/ 08 октября 2018

В Java 8 написание JSON под рукой.

Вы не указали, какой JSON API вы хотите, поэтому я предполагаю, что под "объектом JSON" вы подразумеваете строку с сериализованным объектом JSON.

Что я сделал в проекте CSV Cruncher :

  1. Загрузите CSV, используя HSQLDB .Это относительно небольшая (~ 2 МБ) библиотека, которая фактически реализует базу данных SQL 2008.
  2. Запрос этой базы данных с использованием JDBC.
  3. Создание объекта JSON JDK (javax.json.JsonObject) и его сериализация.

Вот как это сделать:

static void convertResultToJson(ResultSet resultSet, Path destFile, boolean printAsArray) 
{
            OutputStream outS = new BufferedOutputStream(new FileOutputStream(destFile.toFile()));
            Writer outW = new OutputStreamWriter(outS, StandardCharsets.UTF_8);

            // javax.json way
            JsonObjectBuilder builder = Json.createObjectBuilder();
            // Columns
            for (int colIndex = 1; colIndex <= metaData.getColumnCount(); colIndex++) {
                addTheRightTypeToJavaxJsonBuilder(resultSet, colIndex, builder);
            }
            JsonObject jsonObject = builder.build();
            JsonWriter writer = Json.createWriter(outW);
            writer.writeObject(jsonObject);

Весь смысл здесь .(Первоначально я написал свой собственный анализ CSV и запись в JSON, но выяснил, что оба достаточно сложны, чтобы получить доступ к проверенной стандартной библиотеке.)

1 голос
/ 16 марта 2014

Я использовал файл Excel в этом коде. Вы можете использовать CSV.Я написал этот класс для определенного формата Excel / CSV, который мне известен.

import java.io.File;

public class ReadExcel {

    private String inputFile;

    public void setInputFile(String inputFile) {
        this.inputFile = inputFile;
    }

    public void read() throws IOException {
        File inputWorkbook = new File(inputFile);
        Workbook w;
        try {
            w = Workbook.getWorkbook(inputWorkbook);
            // Get the first sheet
            Sheet sheet = w.getSheet(0);
            // Loop over first 10 column and lines
            int columns = sheet.getColumns();
            int rows = sheet.getRows();
            ContactList clist = new ContactList();
            ArrayList<Contact> contacts = new ArrayList<Contact>();
            for (int j = 1; j < rows; j++) {
                Contact contact = new Contact();
                for (int i = 0; i < columns; i++) {
                    Cell cell = sheet.getCell(i, j);

                    switch (i) {
                    case 0:
                        if (!cell.getContents().equalsIgnoreCase("")) {
                            contact.setSrNo(Integer.parseInt(cell.getContents()));
                        } else {
                            contact.setSrNo(j);
                        }

                        break;
                    case 1:
                        contact.setName(cell.getContents());
                        break;
                    case 2:
                        contact.setAddress(cell.getContents());
                        break;
                    case 3:
                        contact.setCity(cell.getContents());
                        break;
                    case 4:
                        contact.setContactNo(cell.getContents());
                        break;
                    case 5:
                        contact.setCategory(cell.getContents());
                        break;
                    }

                }
                contacts.add(contact);

            }
            System.out.println("done");
            clist.setContactList(contacts);
            JSONObject jsonlist = new JSONObject(clist);
            File f = new File("/home/vishal/Downloads/database.txt");
            FileOutputStream fos = new FileOutputStream(f, true);
            PrintStream ps = new PrintStream(fos);

            ps.append(jsonlist.toString());

        } catch (BiffException e) {
            e.printStackTrace();
            System.out.println("error");
        }
    }

    public static void main(String[] args) throws IOException {
        ReadExcel test = new ReadExcel();
        test.setInputFile("/home/vishal/Downloads/database.xls");
        test.read();
    }
}

Я использовал jxl.jar для чтения Excel

0 голосов
/ 05 июня 2019

Вот класс, сгенерированный мной для возврата JSONArray, а не только для печати в файл.

import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.dataformat.csv.CsvMapper;
import com.fasterxml.jackson.dataformat.csv.CsvSchema;
import org.json.simple.JSONArray;
import org.json.simple.parser.JSONParser;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;


import java.io.File;
import java.util.List;
import java.util.Map;


public class CsvToJson {

private static final Logger log = LoggerFactory.getLogger(UtilsFormat.class);
private static CsvToJson instance;


public static JSONArray convert(File input) throws Exception {

    JSONParser parser = new JSONParser();
    CsvSchema csvSchema = CsvSchema.builder().setUseHeader(true).build();
    CsvMapper csvMapper = new CsvMapper();

    // Read data from CSV file
    List<? extends Object> readAll = csvMapper.readerFor(Map.class).with(csvSchema).readValues(input).readAll();

    ObjectMapper mapper = new ObjectMapper();

    JSONArray jsonObject = (JSONArray) parser.parse(mapper.writerWithDefaultPrettyPrinter().writeValueAsString(readAll));
    System.out.print(jsonObject.toString());

    return new JSONArray();
}
}
0 голосов
/ 14 июня 2016

Старый пост, но я решил поделиться своим собственным решением.Предполагается, что кавычки используются вокруг запятой в значении.Затем он также удаляет все цитаты.

Этот метод принимает строку в формате CSV.Таким образом, предполагается, что вы уже прочитали файл CSV в строку.Убедитесь, что вы не удалили символы NextLine ('\ n') во время чтения.

Этот метод ни в коем случае не идеален, но это может быть быстрое решение с одним методом в чистой Java, которое вы ищете.

public String CSVtoJSON(String output) {

    String[] lines = output.split("\n");

    StringBuilder builder = new StringBuilder();
    builder.append('[');
    String[] headers = new String[0];

    //CSV TO JSON
    for (int i = 0; i < lines.length; i++) {
        String[] values = lines[i].replaceAll("\"", "").split("۞");

        if (i == 0) //INDEX LIST
        {
            headers = values;
        } else {
            builder.append('{');
            for (int j = 0; j < values.length && j < headers.length; j++) {

                String jsonvalue = "\"" + headers[j] + "\":\"" + values[j] + "\"";
                if (j != values.length - 1) { //if not last value of values...
                    jsonvalue += ',';
                }
                builder.append(jsonvalue);
            }
            builder.append('}');
            if (i != lines.length - 1) {
                builder.append(',');
            }
        }
    }
    builder.append(']');
    output = builder.toString();

    return output;
}
0 голосов
/ 06 июня 2016

Если вы используете Java 8, вы можете сделать что-то вроде этого. Никаких библиотек или сложной логики не требуется.

Во-первых, создайте POJO, представляющий ваш новый объект JSON. В моем примере он называется YourJSONObject и имеет конструктор, принимающий две строки.

То, что делает код, сначала читает файл, а затем создает поток строк на основе строк. (строка эквивалентна строке в вашем CSV-файле).

Затем мы передаем строку в функцию map, которая разделяет ее на запятую и затем создает YourJSONObject.

Все эти объекты затем собираются в список, который мы передаем в конструктор JSONArray.

Теперь у вас есть массив JSONObjects. Затем вы можете вызвать toString () для этого объекта, если хотите увидеть текстовое представление этого.

        JSONArray objects = new JSONArray(Files.readAllLines(Paths.get("src/main/resources/your_csv_file.csv"))
            .stream()
            .map(s -> new YourJSONObject(s.split(",")[0], s.split(",")[1]))
            .collect(toList()));
...