可变变量'index'在seq {}中以无效方式使用? [英] The mutable variable 'index' is used in an invalid way in seq {}?

查看:82
本文介绍了可变变量'index'在seq {}中以无效方式使用?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在下面的代码中,编译器在index <- index + 1上出现错误

In the following code, the compiler gets error on index <- index + 1 with error

错误3可变变量'index'的使用方式无效.闭包不能捕获可变变量.考虑消除这种使用突变的方法,或者通过'ref'和'!'使用堆分配的可变参考单元. d:\ Users .... \ Program.fs 11 22 ConsoleApplication2

Error 3 The mutable variable 'index' is used in an invalid way. Mutable variables cannot be captured by closures. Consider eliminating this use of mutation or using a heap-allocated mutable reference cell via 'ref' and '!'. d:\Users....\Program.fs 11 22 ConsoleApplication2

但是,它被定义为可变的吗?

However, it has been defined as mutable?

let rec iterateTupleMemberTypes (tupleArgTypes: System.Type[]) (columnNames: string[]) startingIndex = 
    seq {
        let mutable index = startingIndex
        for t in tupleArgTypes do
            match t.IsGenericType with
            | true -> iterateTupleMemberTypes (t.GetGenericArguments()) columnNames index |> ignore
            | false ->
                printfn "Name: %s Type: %A" (columnNames.[index]) t
                index <- index + 1
                yield (columnNames.[index]), t
    } |> Map.ofSeq

let myFile = CsvProvider<"""d:\temp\sample.txt""">.GetSample()
let firstRow = myFile.Rows |> Seq.head
let tupleType = firstRow.GetType()
let tupleArgTypes = tupleType.GetGenericArguments()
let m = iterateTupleMemberTypes tupleArgTypes myFile.Headers.Value 0

推荐答案

一个惯用的版本可能如下所示:

An idiomatic version of this might look like the following:

#r @"..\packages\FSharp.Data.2.2.2\lib\net40\FSharp.Data.dll"

open FSharp.Data
open System

type SampleCsv = CsvProvider<"Sample.csv">

let sample = SampleCsv.GetSample()

let rec collectLeaves (typeTree : Type) =
    seq {
        match typeTree.IsGenericType with
        | false -> yield typeTree.Name
        | true -> yield! typeTree.GetGenericArguments() |> Seq.collect collectLeaves
    }

let columnTypes = (sample.Rows |> Seq.head).GetType() |> collectLeaves

let columnDefinitions = columnTypes |> Seq.zip sample.Headers.Value |> Map.ofSeq

let getDefinitions (sample : SampleCsv) = (sample.Rows |> Seq.head).GetType() |> collectLeaves |> Seq.zip sample.Headers.Value |> Map.ofSeq

就个人而言,除非有数百列,否则我不会太担心Map vs Dictionary(并且具有不变的Map)的性能.

Personally, I wouldn't be concerned too much about the performance of Map vs Dictionary (and rather have the immutable Map) unless there are hundreds of columns.

这篇关于可变变量'index'在seq {}中以无效方式使用?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆