Trouble with String.split in F#
Asked Answered
P

5

2

I am having trouble with the following code, I am trying to build a lexer.

Again I am using the examples from F# for Scientists.

    let lines_of_file filename =
       seq { use stream = File.OpenRead filename
             use reader = new StreamReader(stream)
             while not reader.EndOfStream do
             yield reader.ReadLine() };;

    let read_matrix filename =
      lines_of_file filename
      |> Seq.map (String.split [' '])
      |> Seq.map (Seq.map float)
      |> Math.Matrix.of_seq;;

I have the following namespaces declared:-

          open System
          open System.IO
          open System.Runtime.Serialization.Formatters.Binary
          open Microsoft.FSharp.Core

But in the read_matrix function the "split" in "Split.string" is not recognised. Also the intellisense does not recognise "Matrix".

I have tried declaring a lot of namespaces to see if they recognise the method, but nothing works (my intellisense does not even recognise System.Math).

I apologise if this is a stupid question, I have looked all over MSDN and elsewhere but I could not find anything.

Can anyone help me to get VS to recognise "split" and "Matrix"?

Many thanks.

Pliable answered 26/9, 2011 at 15:26 Comment(0)
H
7

There are a few problems. Your casing is wrong. It's Split, not split. It's an instance (not static) method. The separators must be an array, not list. The following works:

let read_matrix filename =
  lines_of_file filename
  |> Seq.map (fun line -> line.Split ' ')
  |> Seq.map (Seq.map float)
  |> Math.Matrix.ofSeq

Incidentally, Math.Matrix.of_seq has been deprecated. It is now Math.Matrix.ofSeq.

Hospitable answered 26/9, 2011 at 15:30 Comment(4)
I tried that, then it tells me that "Split" is not a static method.Pliable
I tried quite a lot with cases etc. to try to get it to work. Thanks for the suggestion though.Pliable
Ok, you edited your answer after my intial comments. But thanks for the working code that's great.Pliable
Small nitpick: you can write the call to Split as "line.Split(' ')" as if it took a character as argument instead of an array of characters. The array argument is listed as 'params' argument in the C# documentation, so a ParamArrayAttribute is attached. F# also honors that attribute (and builds the array for you behind the scenes)Sphalerite
N
5

A common thing to do to make instance methods more natural to use in F# is to define simple helper functions:

let split separators (x:string) = x.Split(separators)
// Can now pipe into it:
lines_of_file filename
|> Seq.map (split [|' '|])
Nanosecond answered 26/9, 2011 at 19:17 Comment(0)
L
1

As for the Math.Matrix method, it is from the f# powerpack that you need to install...

you can read this Stackoverflow thread.. what-happened-to-microsoft-fsharp-math-matrix

Also for the Split issue.. Split is a method on a string instance.. You can not call it as a static method as you did..

ex: "Some string value".Split([|' '|]) is a correct approach to split a string passing the list of delimiters as an array

Literacy answered 26/9, 2011 at 15:32 Comment(1)
Thank you, I got the matrix function to work after installing the power pack, if I could give you a green tick too I would! :)Pliable
L
1

Also for the Split issue.. Split is a method on a string instance.. You can not call it as a static method as you did..

ex: "Some string value".Split([|' '|]) is a correct approach to split a string passing the list of delimiters as an array

Literacy answered 26/9, 2011 at 15:37 Comment(1)
You should edit your first answer to add this new information, then mark this one for deletion.Gregoor
S
0

Now with f# 8, they introduced _.Property as a shorthand for fun x -> x.Property. It will make things simpler and reduce the need to open PowerPack or FSharpX just for those convenient module functions wrapping methods and properties.

let read_matrix filename =
  lines_of_file filename
  |> Seq.map _.Split(' ')    // <-- new stuff
  |> Seq.map (Seq.map float)
  |> Math.Matrix.ofSeq

More details in this other answer here.

Spongin answered 13/6 at 3:43 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.