Wie kann ich CSV-Daten mit JavaScript parsen?

Lesezeit: 11 Minuten

Benutzer-Avatar
Pierre-Gilles Levallois

Wo finde ich JavaScript-Code zum Analysieren von CSV-Daten?

  • Schauen Sie sich diese Antwort hier an, sie hat gute Antworten: stackoverflow.com/questions/8493195/…

    – Dobes Vandermeer

    8. Februar 2012 um 8:17 Uhr

  • Die meisten der folgenden Antworten sind einfach falsch, abgesehen von der von Andy. Jede Antwort, die Musterabgleich oder Splits verwendet, ist zum Scheitern verurteilt – sie unterstützen keine Escape-Sequenzen. Dafür braucht man einen endlichen Zustandsautomaten.

    – grau.kindel

    17. Januar 2013 um 22:33 Uhr

  • Analysieren einer lokalen CSV-Datei mit JavaScript und Papa Parse: joyofdata.de/blog/…

    – Raffael

    11. August 2014 um 6:09 Uhr


  • Papa Parse ist eine weitere Option mit vielen Funktionen (Multithreading, Kopfzeilenunterstützung, automatische Erkennung von Trennzeichen und mehr)

    – Hinrich

    24. August 2015 um 19:13 Uhr

  • Hinweis für Leute, die über die Suche oder auf andere Weise darauf stoßen; Dies ist kein Beispiel für eine gute Frage. Damals, als Stack Overflow anfing, waren diese Art von Fragen erlaubt.

    – Ketzeraffe

    1. September 2020 um 13:22 Uhr

Benutzer-Avatar
Kirtan

Du kannst den … benutzen CSVToArray() in diesem Blogeintrag erwähnte Funktion.

<script type="text/javascript">
    // ref: http://stackoverflow.com/a/1293163/2343
    // This will parse a delimited string into an array of
    // arrays. The default delimiter is the comma, but this
    // can be overriden in the second argument.
    function CSVToArray( strData, strDelimiter ){
        // Check to see if the delimiter is defined. If not,
        // then default to comma.
        strDelimiter = (strDelimiter || ",");

        // Create a regular expression to parse the CSV values.
        var objPattern = new RegExp(
            (
                // Delimiters.
                "(\\" + strDelimiter + "|\\r?\\n|\\r|^)" +

                // Quoted fields.
                "(?:\"([^\"]*(?:\"\"[^\"]*)*)\"|" +

                // Standard fields.
                "([^\"\\" + strDelimiter + "\\r\\n]*))"
            ),
            "gi"
            );


        // Create an array to hold our data. Give the array
        // a default empty first row.
        var arrData = [[]];

        // Create an array to hold our individual pattern
        // matching groups.
        var arrMatches = null;


        // Keep looping over the regular expression matches
        // until we can no longer find a match.
        while (arrMatches = objPattern.exec( strData )){

            // Get the delimiter that was found.
            var strMatchedDelimiter = arrMatches[ 1 ];

            // Check to see if the given delimiter has a length
            // (is not the start of string) and if it matches
            // field delimiter. If id does not, then we know
            // that this delimiter is a row delimiter.
            if (
                strMatchedDelimiter.length &&
                strMatchedDelimiter !== strDelimiter
                ){

                // Since we have reached a new row of data,
                // add an empty row to our data array.
                arrData.push( [] );

            }

            var strMatchedValue;

            // Now that we have our delimiter out of the way,
            // let's check to see which kind of value we
            // captured (quoted or unquoted).
            if (arrMatches[ 2 ]){

                // We found a quoted value. When we capture
                // this value, unescape any double quotes.
                strMatchedValue = arrMatches[ 2 ].replace(
                    new RegExp( "\"\"", "g" ),
                    "\""
                    );

            } else {

                // We found a non-quoted value.
                strMatchedValue = arrMatches[ 3 ];

            }


            // Now that we have our value string, let's add
            // it to the data array.
            arrData[ arrData.length - 1 ].push( strMatchedValue );
        }

        // Return the parsed data.
        return( arrData );
    }

</script>

  • Es gibt undefined zum Leerfelder das ist zitiert. Beispiel: CSVToArray("4,,6") gibt mir [["4","","6"]]aber CSVToArray("4,\"\",6") gibt mir [["4",undefined,"6"]].

    – Schmerz

    14. November 2012 um 4:36 Uhr

  • Ich hatte Probleme damit in Firefox und das Skript reagiert nicht mehr. Es schien jedoch nur wenige Benutzer zu betreffen, daher konnte die Ursache nicht gefunden werden

    – JDandChips

    18. März 2013 um 11:51 Uhr

  • Es gibt einen Fehler in der Regex: "([^\"\\" should be "([^\\". Otherwise a double quote anywhere in an unquoted value will prematurely end it. Found this the hard way…

    – Walter Tross

    Nov 30, 2015 at 21:52

  • For anyone looking for a reduced version of the above method, with the regex fix described above applied: gist.github.com/Jezternz/c8e9fafc2c114e079829974e3764db75

    – Josh Mc

    Sep 23, 2018 at 1:39


  • Borrowed from @JoshMc (thanks!) and added header capability and more robust character escaping. See gist.github.com/plbowers/7560ae793613ee839151624182133159

    – Peter Bowers

    Dec 29, 2018 at 12:18


user avatar
Evan Plaice

jQuery-CSV

It’s a jQuery plugin designed to work as an end-to-end solution for parsing CSV into JavaScript data. It handles every single edge case presented in RFC 4180, as well as some that pop up for Excel/Google spreadsheet exports (i.e., mostly involving null values) that the specification is missing.

Example:

track,artist,album,year

Dangerous,’Busta Rhymes’,’When Disaster Strikes’,1997

// Calling this
music = $.csv.toArrays(csv)

// Outputs...
[
  ["track", "artist", "album", "year"],
  ["Dangerous", "Busta Rhymes", "When Disaster Strikes", "1997"]
]console.log(musik[1][2]) // Ausgaben: 'When Disaster Strikes'

Aktualisieren:

Oh ja, ich sollte wahrscheinlich auch erwähnen, dass es vollständig konfigurierbar ist.

music = $.csv.toArrays(csv, {
  delimiter: "'", // Sets a custom value delimiter character
  separator: ';', // Sets a custom field separator character
});

Aktualisierung 2:

Es funktioniert jetzt auch mit jQuery auf Node.js. Sie haben also die Möglichkeit, mit derselben Bibliothek entweder clientseitig oder serverseitig zu parsen.

Aktualisierung 3:

Seit der Abschaltung von Google Code jquery-csv wurde auf GitHub migriert.

Haftungsausschluss: Ich bin auch der Autor von jQuery-CSV.

  • Warum ist es jQuery csv? Warum hängt es von jQuery ab? Ich habe die Quelle schnell durchsucht … es sieht nicht so aus, als würden Sie jQuery verwenden

    – paulslater19

    10. Mai 2012 um 8:20 Uhr

  • @paulslater19 Das Plugin ist nicht von jquery abhängig. Vielmehr folgt es den gängigen jQuery-Entwicklungsrichtlinien. Alle enthaltenen Methoden sind statisch und befinden sich unter ihrem eigenen Namespace (dh $.csv). Um sie ohne jQuery zu verwenden, erstellen Sie einfach ein globales $-Objekt, an das sich das Plugin während der Initialisierung bindet.

    – Evan Scholle

    19. November 2012 um 20:48 Uhr

  • ist csv im Lösungscode beziehen sich auf die .csv filename? Ich interessiere mich für ein gutes JS/JQuery-Tool zum Analysieren einer CSV-Datei

    – hüpfendes Nilpferd

    22. November 2012 um 19:59 Uhr

  • @bouncingHippo Im Beispiel bezieht es sich nur auf eine Zeichenfolge von CSV-Daten, aber die Bibliothek kann verwendet werden, um CSV-Dateien lokal im Browser mithilfe der HTML5-Datei-API zu öffnen. Hier ist ein Beispiel dafür in Aktion jquery-csv.googlecode.com/git/examples/file-handling.html.

    – Evan Scholle

    23. November 2012 um 22:09 Uhr

  • Da es nicht von jQuery abhängig ist, wäre es besser, die globale “$”-Abhängigkeit zu entfernen und Benutzern die Möglichkeit zu geben, jede gewünschte Objektreferenz zu übergeben. Vielleicht standardmäßig jQuery, wenn es verfügbar ist. Es gibt andere Bibliotheken, die “$” verwenden, und es kann von Entwicklungsteams mit minimalen Proxys dieser Bibliotheken verwendet werden.

    – RobG

    8. Juli 2018 um 6:47 Uhr


Benutzer-Avatar
Trevor Dixon

Hier ist ein extrem einfacher CSV-Parser, der Felder in Anführungszeichen mit Kommas, neuen Zeilen und doppelten Anführungszeichen mit Escapezeichen behandelt. Es gibt keine Aufteilung oder reguläre Ausdrücke. Es scannt die Eingabezeichenfolge 1-2 Zeichen gleichzeitig und erstellt ein Array.

Testen Sie es bei http://jsfiddle.net/vHKYH/.

function parseCSV(str) {
    var arr = [];
    var quote = false;  // 'true' means we're inside a quoted field

    // Iterate over each character, keep track of current row and column (of the returned array)
    for (var row = 0, col = 0, c = 0; c < str.length; c++) {
        var cc = str[c], nc = str[c+1];        // Current character, next character
        arr[row] = arr[row] || [];             // Create a new row if necessary
        arr[row][col] = arr[row][col] || '';   // Create a new column (start with empty string) if necessary

        // If the current character is a quotation mark, and we're inside a
        // quoted field, and the next character is also a quotation mark,
        // add a quotation mark to the current column and skip the next character
        if (cc == '"' && quote && nc == '"') { arr[row][col] += cc; ++c; continue; }

        // If it's just one quotation mark, begin/end quoted field
        if (cc == '"') { quote = !quote; continue; }

        // If it's a comma and we're not in a quoted field, move on to the next column
        if (cc == ',' && !quote) { ++col; continue; }

        // If it's a newline (CRLF) and we're not in a quoted field, skip the next character
        // and move on to the next row and move to column 0 of that new row
        if (cc == '\r' && nc == '\n' && !quote) { ++row; col = 0; ++c; continue; }

        // If it's a newline (LF or CR) and we're not in a quoted field,
        // move on to the next row and move to column 0 of that new row
        if (cc == '\n' && !quote) { ++row; col = 0; continue; }
        if (cc == '\r' && !quote) { ++row; col = 0; continue; }

        // Otherwise, append the current character to the current column
        arr[row][col] += cc;
    }
    return arr;
}

  • Das wirkt sauberer und geradliniger. Ich musste eine 4-MB-Datei analysieren und die anderen Antworten stürzten bei mir in IE8 ab, aber das hat es geschafft.

    – Charles Clayton

    22. Juni 2014 um 15:26 Uhr


  • Dies hat auch für mich funktioniert. Ich musste jedoch eine Änderung vornehmen, um die korrekte Handhabung von Zeilenvorschüben zu ermöglichen: if (cc == '\r' && nc == '\n' && !quote) { ++row; col = 0; ++c; continue; } if (cc == '\n' && !quote) { ++row; col = 0; continue; }

    – Benutzer655063

    8. April 2015 um 13:00 Uhr


  • Ein anderer Benutzer (@sorin-postelnicu) hat hilfreicherweise eine Begleitfunktion veröffentlicht, um das Ergebnis in ein Wörterbuchobjekt umzuwandeln: jsfiddle.net/8t2po6wh.

    – Trevor Dixon

    20. Oktober 2017 um 12:37 Uhr

  • Ja, wann immer Geschwindigkeit benötigt wird oder Speicherbedarf eine Rolle spielt, ist eine saubere Lösung wie diese weit überlegen. State-Machine-artiges Parsen ist so viel glatter.

    – Tatarisieren

    9. August 2018 um 5:22 Uhr

  • Verwandeln Sie es in einen Generator, der nachgibt, und Sie haben eine Möglichkeit, mit größeren Datenmengen umzugehen: Beispiel

    – Endlos

    16. November 2020 um 20:29 Uhr

Benutzer-Avatar
Andy VanWagoner

Ich habe eine Implementierung als Teil eines Tabellenkalkulationsprojekts.

Dieser Code ist noch nicht gründlich getestet, aber jeder kann ihn gerne verwenden.

Wie einige der Antworten jedoch anmerkten, kann Ihre Implementierung viel einfacher sein, wenn Sie dies tatsächlich getan haben DSV oder TSV -Datei, da sie die Verwendung von Datensatz- und Feldtrennzeichen in den Werten nicht zulassen. CSV hingegen kann tatsächlich Kommas und Zeilenumbrüche innerhalb eines Felds enthalten, was die meisten regulären Ausdrücke und Split-basierten Ansätze durchbricht.

var CSV = {
    parse: function(csv, reviver) {
        reviver = reviver || function(r, c, v) { return v; };
        var chars = csv.split(''), c = 0, cc = chars.length, start, end, table = [], row;
        while (c < cc) {
            table.push(row = []);
            while (c < cc && '\r' !== chars[c] && '\n' !== chars[c]) {
                start = end = c;
                if ('"' === chars[c]){
                    start = end = ++c;
                    while (c < cc) {
                        if ('"' === chars[c]) {
                            if ('"' !== chars[c+1]) {
                                break;
                            }
                            else {
                                chars[++c] = ''; // unescape ""
                            }
                        }
                        end = ++c;
                    }
                    if ('"' === chars[c]) {
                        ++c;
                    }
                    while (c < cc && '\r' !== chars[c] && '\n' !== chars[c] && ',' !== chars[c]) {
                        ++c;
                    }
                } else {
                    while (c < cc && '\r' !== chars[c] && '\n' !== chars[c] && ',' !== chars[c]) {
                        end = ++c;
                    }
                }
                row.push(reviver(table.length-1, row.length, chars.slice(start, end).join('')));
                if (',' === chars[c]) {
                    ++c;
                }
            }
            if ('\r' === chars[c]) {
                ++c;
            }
            if ('\n' === chars[c]) {
                ++c;
            }
        }
        return table;
    },

    stringify: function(table, replacer) {
        replacer = replacer || function(r, c, v) { return v; };
        var csv = '', c, cc, r, rr = table.length, cell;
        for (r = 0; r < rr; ++r) {
            if (r) {
                csv += '\r\n';
            }
            for (c = 0, cc = table[r].length; c < cc; ++c) {
                if (c) {
                    csv += ',';
                }
                cell = replacer(r, c, table[r][c]);
                if (/[,\r\n"]/.test(cell)) {
                    cell=""" + cell.replace(/"/g, '""') + '"';
                }
                csv += (cell || 0 === cell) ? cell : '';
            }
        }
        return csv;
    }
};

Benutzer-Avatar
dt192

csvToArray v1.3

Eine kompakte (645 Bytes), aber konforme Funktion zum Konvertieren einer CSV-Zeichenfolge in ein 2D-Array, die dem RFC4180-Standard entspricht.

https://code.google.com/archive/p/csv-to-array/downloads

Häufige Verwendung: jQuery

 $.ajax({
        url: "test.csv",
        dataType: 'text',
        cache: false
 }).done(function(csvAsString){
        csvAsArray=csvAsString.csvToArray();
 });

Häufige Verwendung: JavaScript

csvAsArray = csvAsString.csvToArray();

Feldtrenner überschreiben

csvAsArray = csvAsString.csvToArray("|");

Datensatztrennzeichen überschreiben

csvAsArray = csvAsString.csvToArray("", "#");

Kopfzeile überspringen überschreiben

csvAsArray = csvAsString.csvToArray("", "", 1);

Alles überschreiben

csvAsArray = csvAsString.csvToArray("|", "#", 1);

  • Das klingt interessant, aber ich kann den Code jetzt nicht finden. Kannst du es nochmal posten?

    – Sam Watkins

    3. April 2018 um 3:37 Uhr

  • Ich habe den Hauptbeitrag mit einem aktuellen Link aktualisiert. Danke vielmals.

    – dt192

    4. April 2018 um 9:25 Uhr


  • Es befindet sich im Google Code-Archiv, aber vielleicht auf einen neuen Speicherort aktualisieren?

    – Peter Mortensen

    1. September 2020 um 13:36 Uhr

Benutzer-Avatar
Trevor Dixon

Hier ist meine PEG(.js)-Grammatik, die bei RFC 4180 in Ordnung zu sein scheint (dh sie behandelt die Beispiele bei http://en.wikipedia.org/wiki/Comma-separated_values):

start
  = [\n\r]* first:line rest:([\n\r]+ data:line { return data; })* [\n\r]* { rest.unshift(first); return rest; }

line
  = first:field rest:("," text:field { return text; })*
    & { return !!first || rest.length; } // ignore blank lines
    { rest.unshift(first); return rest; }

field
  = '"' text:char* '"' { return text.join(''); }
  / text:[^\n\r,]* { return text.join(''); }

char=""" '"' { return '"'; }
  / [^"]

Probieren Sie es aus http://jsfiddle.net/knvzk/10 oder http://pegjs.majda.cz/online. Laden Sie den generierten Parser unter herunter https://gist.github.com/3362830.

  • Das klingt interessant, aber ich kann den Code jetzt nicht finden. Kannst du es nochmal posten?

    – Sam Watkins

    3. April 2018 um 3:37 Uhr

  • Ich habe den Hauptbeitrag mit einem aktuellen Link aktualisiert. Danke vielmals.

    – dt192

    4. April 2018 um 9:25 Uhr


  • Es befindet sich im Google Code-Archiv, aber vielleicht auf einen neuen Speicherort aktualisieren?

    – Peter Mortensen

    1. September 2020 um 13:36 Uhr

Benutzer-Avatar
Peter Mortensen

Hier ist mein einfacher Vanilla-JavaScript-Code:

let a="one,two,"three, but with a comma",four,"five, with ""quotes"" in it..""
console.log(splitQuotes(a))

function splitQuotes(line) {
  if(line.indexOf('"') < 0) 
    return line.split(',')

  let result = [], cell="", quote = false;
  for(let i = 0; i < line.length; i++) {
    char = line[i]
    if(char == '"' && line[i+1] == '"') {
      cell += char
      i++
    } else if(char == '"') {
      quote = !quote;
    } else if(!quote && char == ',') {
      result.push(cell)
      cell=""
    } else {
      cell += char
    }
    if ( i == line.length-1 && cell) {
      result.push(cell)
    }
  }
  return result
}

1018690cookie-checkWie kann ich CSV-Daten mit JavaScript parsen?

This website is using cookies to improve the user-friendliness. You agree by using the website further.

Privacy policy