Core Function CSV
CSV( <string>, <delim>, <quote>, <quoteescape>, <comment>, <trimtype> )
Contents |
Description
Split strings and parse a CSV text into an array.
This function is useful for reading columns of data from a text file where the columns (fields) are delimited with a specific character or characters.
Parameters
string
The string to parse.
delim
Optional; The Char to use as the Delimiter for seperation of the data.
Default is ','
quote
Optional; The Char to use as the Quote this will be allowed to contain the Delimiter inside it.
Default is '"'
quoteescape
Optional; The Char to use for escaping the Quote this will be used to allow a Quote to appear inside quotes.
Default is "\\"
comment
Optional; The Char to use as the Comment and it will be removed from the text with no side effects.
Default is '#'
Can be set to "\0" to disable need for comment
trimtype
Optional; Determines how values should be trimmed.
0 = Trim Unquoted Only (Default)
1 = Trim Quoted Only
2 = Trim All
3 = Trim None
Default is: 0
Return Value
Success: Returns a 2 dimensional array where the first dimension is the LINES or ROWS and the second dimension is the parsed data in an array.
Failure: Returns empty array.
Remarks
CSV Parsing is better than simply using Split() on complex data since Split() does not think about finding the split char inside "" quotes etc where as this CSV function does.
This CSV parser supports fields spanning multiple lines. The only restriction is that they must be quoted, otherwise it would not be possible to distinguish between malformed data and multi-line values.
Example
A simple split a string using , for the Delimiter
$a = "100, 200, 300"; foreach(CSV($a)[0] as $item) { println("Item '$item'"); }
A more complex split where the , Delimiter is also contained within ' string '
$a = "100, 200, '47, 77', 300, 400, 500"; foreach(CSV($a, ",", "'")[0] as $item) { println("Item '$item'"); }
A larger example involving multiple lines of text to parse and the , Delimiter is also contained within ' string '
$a = "100, 200, '47, 77', 300, 400, 500\n"; $a .= "122.33 'hello, yay', 55, 77\n"; $a .= "a, b, c, d"; foreach(CSV($a, ",", "'") as $lines) { println("ROW BEGINS"); foreach($lines as $item) { println("Item '$item'"); } println("ROW ENDS"); }
Example of having a Quote inside quotes using the QuiteEscape param
$a = "100, 200, '47, \\'77', 300, 400, 500"; foreach(CSV($a, ",", "'", '\\')[0] as $item) { println("Item '$item'"); }
Here is a hand made CSV parser in Sputnik (do not use this it is only here as an example! the CSV() function is WAY better trust me)
// Parse some stuff my $arr = ParseCSV("Cat,Dog,FoX,'hehe,lol',hi"); // Print the result printr $arr; // PRINTS // Array // ( // [0] => 5 // [1] => Array // ( // [0] => Cat // [1] => Dog // [2] => FoX // [3] => "hehe,lol" // [4] => hi // ) // ) // Define a CSV parsing function // this is actually a direct port from my 15+ year old // PERL source code it is pretty sloppy but it does // work for what i needed to do at the time Function ParseCSV($InStr, $AlternativeSplit = null) { my $SplitChar = ','; if ($AlternativeSplit) $SplitChar = $AlternativeSplit; my $FoundFirst = 0; my $FoundSecond = 0; my $StartChar = 0; my $ParamCharCount = 0; my $ParamArray = array(); my $ParamCount = 0; my $IsAnyOn; my $CurrentlyInParam; $InStr .= $SplitChar; # Add , to end to avoid issues... $InStr = Replace($InStr, "'", '"'); for (my $Count = 0; $Count <= strlen($InStr); $Count++) { my $StrBit = substr($InStr, $Count, 1); if($StrBit) { # First quote now lets find next one... if($StrBit == "\"" && $FoundFirst == 0) $FoundFirst = 1; # Second quote now we are free to end on comma else if($StrBit == "\"" && $FoundFirst == 1) $FoundFirst= 0; # First quote now lets find next one... if($StrBit == '(') $FoundSecond++; # Second quote now we are free to end on comma else if($StrBit == ')') $FoundSecond--; $IsAnyOn = 0; if($FoundFirst == 1) $IsAnyOn = 1; if($FoundSecond > 0) $IsAnyOn = 1; if($IsAnyOn == 1) $CurrentlyInParam = 1; else $CurrentlyInParam = 0; # Comma with no FoundFirst = we found the end! if($StrBit eq $SplitChar && $CurrentlyInParam == 0) { my $FinalParam = substr($InStr, $StartChar, $ParamCharCount); # Remove , if it is at end of string $FinalParam =~ s/$SplitChar$//; $StartChar = $Count; $StartChar++; # Make sure we dont get , on next one... $ParamCharCount = 0; if(strlen($FinalParam) > 0) { push($ParamArray, $FinalParam); $ParamCount++; } } } $ParamCharCount++; } if($CurrentlyInParam == 1) { print "Parse failed!, Didnt find closing bracket/quote!\n"; print "$InStr\n"; } return array($ParamCount, $ParamArray); }