F#:将单个元素包装到数组

F#:将单个元素包装到数组,f#,F#,在F#中,如何使函数包装器(x:'T)将任何输入包装到数组中,例如:wrapper(1)=[|[| 1 |][124;];包装器([| 1 |])=[|[| 1 |][124;];和包装器([|[| 1 |][124;])=[|[| 1 |][124;]以下类似内容不起作用: let wrapper (x:'T) = let y = if not <| x.GetType().IsArray then [|[|x|]|] elif not <

在F#中,如何使函数
包装器(x:'T)
将任何输入包装到数组中,例如:
wrapper(1)=[|[| 1 |][124;];包装器([| 1 |])=[|[| 1 |][124;];和包装器([|[| 1 |][124;])=[|[| 1 |][124;]以下类似内容不起作用:

let wrapper (x:'T) = 
    let y = 
        if not <| x.GetType().IsArray then [|[|x|]|]
        elif not <| x.[0].GetType().IsArray then [|x|]
        else x
    y
let wrapper(x:'T)=
设y=

如果不您不能,那么这不是一个类型良好的函数(请尝试写出类型签名)。

您不能,这不是一个类型良好的函数(请尝试写出类型签名)。

以下操作似乎有效:

let wrapper<'a, 'b> (x:'a) = 
  match box x with
  | null -> null
  | :? array<array<'b>> as y -> y
  | :? array<'b> as y -> [|y|]
  | y -> [|[|unbox y|]|]
let包装器(x:'a)=
将方框x与
|空->空
| :? 数组形式为y->[| y |]
|y->[|[|解X y |][124;]

签名是
'a->array以下内容似乎有效:

let wrapper<'a, 'b> (x:'a) = 
  match box x with
  | null -> null
  | :? array<array<'b>> as y -> y
  | :? array<'b> as y -> [|y|]
  | y -> [|[|unbox y|]|]
let包装器(x:'a)=
将方框x与
|空->空
| :? 数组形式为y->[| y |]
|y->[|[|解X y |][124;]

签名是
'a->array这是一个基于反射的解决方案,它将接受任意嵌套数组深度的输入:

open System.Text.RegularExpressions
let wrapper input =
    let ty = input.GetType()
    if ty.IsArray |> not then
        [|[|input |> unbox|]|]
    else
        let depth = Regex.Matches(ty.Name, "\[\]", RegexOptions.Compiled).Count
        let rec findInnerItem curDepth curArray =
            let innerItem = curArray.GetType().GetMethod("Get").Invoke(curArray, [|box 0|])
            if curDepth = depth then
                innerItem
            else
                findInnerItem (curDepth+1) innerItem

        let innerItem = findInnerItem 1 input
        [|[|innerItem |> unbox|]|]
在FSI中的用法:

val wrapper : 'a -> 'b [] []

> let x : int[][] = wrapper 1;;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|1|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|1|]|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|[|1|]|]|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|[|[|1|]|]|]|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|[|[|[|1|]|]|]|]|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|[|[|[|[|1|]|]|]|]|]|];;

val x : int [] [] = [|[|1|]|]

下面是一个基于反射的解决方案,它将接受任意嵌套数组深度的输入:

open System.Text.RegularExpressions
let wrapper input =
    let ty = input.GetType()
    if ty.IsArray |> not then
        [|[|input |> unbox|]|]
    else
        let depth = Regex.Matches(ty.Name, "\[\]", RegexOptions.Compiled).Count
        let rec findInnerItem curDepth curArray =
            let innerItem = curArray.GetType().GetMethod("Get").Invoke(curArray, [|box 0|])
            if curDepth = depth then
                innerItem
            else
                findInnerItem (curDepth+1) innerItem

        let innerItem = findInnerItem 1 input
        [|[|innerItem |> unbox|]|]
在FSI中的用法:

val wrapper : 'a -> 'b [] []

> let x : int[][] = wrapper 1;;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|1|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|1|]|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|[|1|]|]|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|[|[|1|]|]|]|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|[|[|[|1|]|]|]|]|];;

val x : int [] [] = [|[|1|]|]

> let x : int[][] = wrapper [|[|[|[|[|[|1|]|]|]|]|]|];;

val x : int [] [] = [|[|1|]|]
函数需要“将任何输入包装到数组的数组中”。正如这个陈述一样,这个解决方案和

一样简单。
let wrapper (x:'T) = [|[|x|]|];

但是,你给出的例子不如你的函数定义。 I.<代码>包装器(〔1〕)=[[〔1〕]〕/代码>应<代码>包装器(〔1〕)=[[〔1〕] ] < /COD>作为PAR您的函数定义。

< p>您需要“将任何输入包到数组的数组”。正如这个陈述一样,这个解决方案和

一样简单。
let wrapper (x:'T) = [|[|x|]|];

但是,你给出的例子不如你的函数定义。


E.<代码>包装器(〔1〕)=[[〔1〕〕] <代码>应为<代码>包装器〔〔1〕〕=〔[〔〔1〕〕〕< /代码>为您的函数定义。

谢谢。像python这样的动态类型语言会允许这样的函数吗?@matlabdbuser-任何.NET语言都可以像典型的动态语言一样使用
System.Reflection
完成很多工作。现在,随着.NET 4.0中的DLR与C#的静态
动态
和F#的
操作符等内置语言功能的结合,差距更大了。@matlabdbuser-正如其他一些答案所示,只要给函数一个相对不具信息性的类型,就有可能在F#中实现此功能(例如,
obj->obj
,或
'a->'b[][]
)对我来说,问题是你为什么想要一个这样的函数。当你与类型系统进行如此激烈的斗争时,如果你后退一步并分析你的需求,这通常表明有一种更惯用的方法来解决你的问题。@kvb-如果我想做一个函数来转换
string[],string[],float[],float[],int[],int[],bool[],bool[],bool[]等等…
到键入的
数据表,以及1d数组
't[]
我想让它用一列而不是一行来填充数据表,我想得到我的问题中的包装函数会很方便吗?谢谢。像python这样的动态类型语言会允许这样的函数吗?@matlabdbuser-任何.NET语言都可以像典型的动态语言一样使用
System.Reflection
。和NET 4.0中的DLR与C#的静态
动态
和F#的
操作符等内置语言功能结合在一起,差距就更大了。@matlabdbuser-正如其他一些答案所示,只要给函数一个相对不具信息性的类型,就有可能在F#中实现此功能(例如,
obj->obj
,或
'a->'b[][]
)对我来说,问题是你为什么想要一个这样的函数。当你与类型系统进行如此激烈的斗争时,如果你后退一步并分析你的需求,这通常表明有一种更惯用的方法来解决你的问题。@kvb-如果我想做一个函数来转换
string[],string[],float[],float[],int[],int[],bool[],bool[],bool[]等等…
到键入的
数据表,以及1d数组
't[]
我希望它以一列而不是一行来填充数据表,我认为像我的问题中那样获得包装函数会很方便?如果你想在F#中这样做,你可能做错了什么。如果你想在F#中这样做,你可能做错了什么。