Advertisement
Guest User

Untitled

a guest
Mar 31st, 2015
201
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 3.49 KB | None | 0 0
  1. var Parser = (function() {
  2.  
  3. var QUOTE = '"';
  4. var NEW_LINE = '\n';
  5. var DELIMITER = ',';
  6. var newLineLength = NEW_LINE.length;
  7. var delimiterLength = DELIMITER.length;
  8.  
  9. function parse(input) {
  10.  
  11. var index = 0,
  12. EOFIndex = input.length,
  13. beginCaptureIndex = -1,
  14. endCaptureIndex = -1,
  15. delimiterIndex = -1,
  16. newLineIndex = -1,
  17. rows = [],
  18. row = [];
  19.  
  20. for (; EOFIndex ;) {
  21.  
  22. // quoted field
  23. if (charAt(index) === QUOTE) {
  24.  
  25. // field start index without opening quote
  26. beginCaptureIndex = index + 1;
  27.  
  28. // consume string until we find a quote or reach the EOF
  29. while (isEOF(index) ? false : charAt(++index) === QUOTE ?
  30. // true (continue) : next char is a quote, this is an escaped quote / part of the data
  31. // false (stop) : next char is not a quote, we found the fields terminating quote
  32. charAt(++index) === QUOTE :
  33. // was not a quote, keep going
  34. true
  35. ){}
  36.  
  37. // field end index without closing quote
  38. endCaptureIndex = index - 1;
  39.  
  40. push(
  41. // unescape quotes within a quoted field
  42. unescape(
  43. input.substring(beginCaptureIndex, endCaptureIndex)
  44. ));
  45.  
  46. } else {
  47.  
  48. // this is not a quoted field which makes finding
  49. // the next delimiter pretty straight forward.
  50. // -1 is an acceptable value
  51. delimiterIndex = findNextDelimiter();
  52.  
  53. // small optimization.. we don't need to find the next newline
  54. // if it is already placed after the delimiter index.
  55. // -1 is an acceptable value
  56. newLineIndex = ~delimiterIndex && ~newLineIndex && delimiterIndex < newLineIndex ?
  57. newLineIndex : findNextNewLine();
  58.  
  59. // the next delimiter comes before the next newline,
  60. // or this is the last line. we've reached the end of a field
  61. if (~delimiterIndex && (delimiterIndex < newLineIndex || !~newLineIndex)) {
  62. endCaptureIndex = delimiterIndex;
  63. } else {
  64.  
  65. // no delimiter was found or the delimier was found after the
  66. // next newline. this is the last field in the row (and possibly the input)
  67. endCaptureIndex = ~newLineIndex ? newLineIndex : EOFIndex;
  68. }
  69.  
  70. push(input.substring(index, index = endCaptureIndex));
  71. }
  72.  
  73. if (isEOF(index)) { // end of file
  74. // save the current row
  75. commitRow();
  76. // bail out
  77. break;
  78. } else if (chars(newLineLength) === NEW_LINE) { // end of a row
  79. // save the current row
  80. commitRow();
  81. // advance index past the newline and continue processing
  82. index += newLineLength;
  83. } else if (chars(delimiterLength) === DELIMITER) { // end of field
  84. // advance index past the delimiter and continue processing
  85. index += delimiterLength;
  86. }
  87. }
  88.  
  89. return rows;
  90.  
  91. ///////////
  92. ///////////
  93.  
  94. function isEOF(i) {
  95. return i >= EOFIndex;
  96. }
  97.  
  98. function charAt(i) {
  99. return input.charAt(i);
  100. }
  101.  
  102. function chars(i) {
  103. return input.substr(index, i);
  104. }
  105.  
  106. function findNextDelimiter() {
  107. return input.indexOf(DELIMITER, index);
  108. }
  109.  
  110. function findNextNewLine() {
  111. return input.indexOf(NEW_LINE, index);
  112. }
  113.  
  114. function push(val) {
  115. return row.push(val);
  116. }
  117.  
  118. function commitRow() {
  119. rows.push(row.splice(0, row.length));
  120. }
  121.  
  122. function unescape(val) {
  123. return val.replace(/""/g, '"');
  124. }
  125. }
  126.  
  127. return {
  128. parse: parse
  129. };
  130. })();
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement