Normalize array throwing an error

I’m trying to normalize data from a CSV file, I’m separating out the columns then attempting to normalize per column but the console is throwing me an error I don’t understand – “String:multiChannelPerform. Cannot expand strings.” could anyone explain what’s going wrong? thanks!

~csvfile_0=Array.fill(~csvfile.size,{arg i;~csvfile.at(i).asArray.at(0)});

~csvfile_0.normalize(100,1000);

-> [ 0.000850007, 0.002550022, 0.004250037, 0.005950051, 0.007650065, 0.00935008, 0.011050095, 0.012750109, 0.014450124, 0.016150137, 0.017850153, 0.019550167, 0.02125018, 0.022950197, 0.02465021, 0.026350226, 0.02805024, 0.029750254, 0.031450268, 0.033150285, 0.0348503, 0.036550313, 0.038250327, 0.03995034, 0.041650355, 0.043350372, 0.045050386, 0.0467504, 0.048450414, 0.050150428, 0.05185044, 0.05355046, 0.055250473, 0.056950487, 0.0586505, 0.060350515, 0.062050533, 0.06375054, 0.06545056, 0.06715058, 0.0688…etc…
ERROR: String:multiChannelPerform. Cannot expand strings.
CALL STACK:
Exception:reportError
arg this =
Nil:handleError
arg this = nil
arg error =
Thread:handleError
arg this =
arg error =
Object:throw
arg this =
String:multiChannelPerform
arg this = “0.000850007”
arg selector = ‘linlin’
arg args = [*4]
< FunctionDef in Method Collection:collectAs >
arg elem = “0.000850007”
arg i = 0
ArrayedCollection:do
arg this = [*1000]
arg function =
var i = 0
Collection:collectAs
arg this = [*1000]
arg function =
arg class =
var res = [*0]
< closed FunctionDef > (no arguments or variables)
Interpreter:interpretPrintCmdLine
arg this =
var res = nil
var func =
var code = “~csvfile_0.normalize(100,1000);”
var doc = nil
var ideClass =
Process:interpretPrintCmdLine
arg this =
^^ The preceding error dump is for ERROR: String:multiChannelPerform. Cannot expand strings.

Hi,
I don’t know what’s in your CSV file, so I tested this with a basic CSV file as a String.
I think you’re calling .normalize on a String (which gives the error), see the example below how to convert all the elements in the CSV to floats.

~csvfile = "0.1, 0.2\n0.3, 0.4"; // Very basic CSV file
~rows = ~csvfile.split($\n); // Example to get rows

~rows[0].postln; // Test
~columnPerRow = ~rows[0].split($,);
~columnPerRow[0].postln; // Still a float!
~columnPerRow.asFloat // Cast each element (now a String) to float

~csvFileAsFloatArray = ~csvfile.split($\n).collect({|row| row.split($,).asFloat}); // <--

thankyou @Jildert, very helpful! unfortunately, I don’t think this forum accepts CSV (?) but it’s just floats, no headers, or nesting etc.

Your example makes sense (SC beginner here) but is there a way I can put .asFloat in/after my Array.fill operation and before normalizing? I don’t think I need the row splitting.

Ah, I just discovered CSVFileReader, you’re using that probably, right?
And to answer your question, I think this will fix the issue:

~csvfile_0.asFloat.normalize(100,1000);

(The .csv may look like it’s filled with float values, but since it’s an ASCII (text) file, they are parsed as being strings (which they are, until your tell SC you want them to be floats (.asFloat)). I hope that makes sense :wink:
Good luck!

1 Like

Thankyou! I tried converting to float before jumping on the forum and must have done something deeply wrong. It works now with your help! and yep, was using CSVFileReader

The strange thing for me is I used another .csv and didn’t need to convert to float (i.e. wasn’t getting the same error on execution) is it that all .csv cells will be ASCII or hit and miss?

Thanks for the help again :raised_hands:

Glad it works!
And expect all values in a .csv file to be a string, since it’s from a text-file.
So you may read 3.14 as a float, your computer (the file parser, CSVFileReader) simply sees four characters (forming a string).
Perhaps you’ve used .readInterpret before? This converts the strings to numbers.