toolkit/javascript/d3/d3.csv.js
changeset 47 c0b4a8b5a012
equal deleted inserted replaced
46:efd9c589177a 47:c0b4a8b5a012
       
     1 (function(){d3.csv = function(url, callback) {
       
     2   d3.text(url, "text/csv", function(text) {
       
     3     callback(text && d3.csv.parse(text));
       
     4   });
       
     5 };
       
     6 d3.csv.parse = function(text) {
       
     7   var header;
       
     8   return d3.csv.parseRows(text, function(row, i) {
       
     9     if (i) {
       
    10       var o = {}, j = -1, m = header.length;
       
    11       while (++j < m) o[header[j]] = row[j];
       
    12       return o;
       
    13     } else {
       
    14       header = row;
       
    15       return null;
       
    16     }
       
    17   });
       
    18 };
       
    19 
       
    20 d3.csv.parseRows = function(text, f) {
       
    21   var EOL = {}, // sentinel value for end-of-line
       
    22       EOF = {}, // sentinel value for end-of-file
       
    23       rows = [], // output rows
       
    24       re = /\r\n|[,\r\n]/g, // field separator regex
       
    25       n = 0, // the current line number
       
    26       t, // the current token
       
    27       eol; // is the current token followed by EOL?
       
    28 
       
    29   re.lastIndex = 0; // work-around bug in FF 3.6
       
    30 
       
    31   /** @private Returns the next token. */
       
    32   function token() {
       
    33     if (re.lastIndex >= text.length) return EOF; // special case: end of file
       
    34     if (eol) { eol = false; return EOL; } // special case: end of line
       
    35 
       
    36     // special case: quotes
       
    37     var j = re.lastIndex;
       
    38     if (text.charCodeAt(j) === 34) {
       
    39       var i = j;
       
    40       while (i++ < text.length) {
       
    41         if (text.charCodeAt(i) === 34) {
       
    42           if (text.charCodeAt(i + 1) !== 34) break;
       
    43           i++;
       
    44         }
       
    45       }
       
    46       re.lastIndex = i + 2;
       
    47       var c = text.charCodeAt(i + 1);
       
    48       if (c === 13) {
       
    49         eol = true;
       
    50         if (text.charCodeAt(i + 2) === 10) re.lastIndex++;
       
    51       } else if (c === 10) {
       
    52         eol = true;
       
    53       }
       
    54       return text.substring(j + 1, i).replace(/""/g, "\"");
       
    55     }
       
    56 
       
    57     // common case
       
    58     var m = re.exec(text);
       
    59     if (m) {
       
    60       eol = m[0].charCodeAt(0) !== 44;
       
    61       return text.substring(j, m.index);
       
    62     }
       
    63     re.lastIndex = text.length;
       
    64     return text.substring(j);
       
    65   }
       
    66 
       
    67   while ((t = token()) !== EOF) {
       
    68     var a = [];
       
    69     while ((t !== EOL) && (t !== EOF)) {
       
    70       a.push(t);
       
    71       t = token();
       
    72     }
       
    73     if (f && !(a = f(a, n++))) continue;
       
    74     rows.push(a);
       
    75   }
       
    76 
       
    77   return rows;
       
    78 };
       
    79 d3.csv.format = function(rows) {
       
    80   return rows.map(d3_csv_formatRow).join("\n");
       
    81 };
       
    82 
       
    83 function d3_csv_formatRow(row) {
       
    84   return row.map(d3_csv_formatValue).join(",");
       
    85 }
       
    86 
       
    87 function d3_csv_formatValue(text) {
       
    88   return /[",\n]/.test(text)
       
    89       ? "\"" + text.replace(/\"/g, "\"\"") + "\""
       
    90       : text;
       
    91 }
       
    92 })();