Steven Steven - 2 months ago 8
R Question

How to create a dataframe of multiple types with the RTypeProvider

It seems like the

RTypeProvider
can only handle
namedParams
of the same type. Is this the case?

For example,

open RDotNet
open RProvider

type foo = {
Which: string
Qty: float option
}

let someFoos = [{Which = "that"; Qty = Some 4.0}; {Which = "other"; Qty = Some 2.0}]

let thingForR =
namedParams [
"which", someFoos |> List.map (fun x -> x.Which);
"qty", someFoos |> List.map (fun x -> x.Qty);
]
|> R.data_frame


doesn't work as I get an error on the
x.Qty
saying

This expression was expected to have type
string
but here has type
float option


If I reverse the order in the
thingForR
let, then I get the opposite error:

let thingForR =
namedParams [
"qty", someFoos |> List.map (fun x -> x.Qty);
"which", someFoos |> List.map (fun x -> x.Which);
]
|> R.data_frame


Here, the error on
x.Which
is

This expression was expected to have type
float option
but here has type
string


Can the dictionary in the
namedParams
not have different types? If so, how can you create a data frame with different types in F# and pass them to R?

Answer

You need to box the values inside the dictionary. That way they are all just object. So:

let thingForR = 
    namedParams [
        "which", box (someFoos |>  List.map (fun x ->  x.Which) ); 
        "qty", box  (someFoos |> List.map (fun x ->   x.Qty) |> List.map (Option.toNullable >> float));
        ]
    |> R.data_frame

gives me:

val thingForR :
SymbolicExpression = which qty
1 that 4
2 other 2

Please refer to your previous question on float option to convert the Option list to float list. Also string option if necessary.

You can go through Deedle (if not for the option values):

let someFoos' = [{Which = "that"; Qty =  4.0}; {Which = "other"; Qty =  2.0}]
let df' = someFoos' |> Frame.ofRecords
df' |> R.data_frame 
Comments