【问题标题】:MathNumerics.LinearAlgebra Matrix.mapRows dimensionality issuesMathNumerics.LinearAlgebra Matrix.mapRows 维度问题
【发布时间】:2016-05-17 03:31:07
【问题描述】:

所以我已经验证了我正在尝试做的起始版本的工作,但由于某种原因,当将它放入 Matrix.map 高阶函数时它会崩溃。

这是失败的功能:

let SumSquares (theta:Vector<float>) (y:Vector<float>) (trainingData:Matrix<float>) =
    let m = trainingData.RowCount
    let theta' = theta.ToRowMatrix()
    trainingData     
    |> Matrix.mapRows(fun a r -> (theta' * r) - y.[a] )

这里有一些示例测试

设置:

let tData = matrix [[1.0; 2.0]
                    [1.0; 3.0]
                    [1.0; 3.0]
                    [1.0; 4.0]]   
let yVals = vector [5.0; 6.0; 7.0; 11.0]      
let theta = vector [1.0; 0.2]  

测试基本操作的原始功能(theta transpose * vector - actual)

let theta' = theta.ToRowMatrix()
(theta.ToRowMatrix() * tData.[0, 0 .. 1]) - yVals.[0]

实际功能测试:

tData |> SumSquares theta yVals

这是实际错误的复制/粘贴。读起来好像我将较大的向量映射到较小的向量时遇到了问题。

参数名称:目标

在 MathNet.Numerics.LinearAlgebra.Storage.VectorStorage1.CopyToRow(MatrixStorage1 目标,Int32 rowIndex,ExistingData existingData)
在 FSI_0061.SumSquares(Vector1 theta, Vector1 y, Matrix`1 trainingData) 在 C:\projects\deleteme\ASPNet5Test\ConsoleApplication1\ConsoleApplication1\MachineLearning.fsx:line 23
在 C:\projects\deleteme\ASPNet5Test\ConsoleApplication1\ConsoleApplication1\MachineLearning.fsx: 39 行中的 .$FSI_0084.main@()
由于错误而停止

【问题讨论】:

  • 这是真正的例外,对吧? System.ArgumentException: All vectors must have the same dimensionality.
  • 感兴趣的:Deep Learning Tag
  • 是的,随着学习算法的进展,我们基本上会将其用作理解成本的一部分

标签: f# linear-algebra math.net mathnet-numerics


【解决方案1】:

我找到了一种更好更简单的方法来做到这一点。我必须感谢 s952163 让我走上了一条好的道路,但这种方法更加优化:

let square (x:Vector<float>) = x * x 
let subtract (x:Vector<float>) (y:Vector<float>) = y - x
let divideBy (x:float) (y:float) = y / x

let SumSquares (theta:Vector<float>) (y:Vector<float>) (trainingData:Matrix<float>) =
    let m = trainingData.RowCount |> float
    (trainingData * theta)
    |> subtract y
    |> square
    |> divideBy m

【讨论】:

    【解决方案2】:

    由于您知道行数,因此您可以映射到该行数。可以说这并不漂亮:

    let SumSquares (theta:Vector<float>) (y:Vector<float>) (trainingData:Matrix<float>) =
        let m = trainingData.RowCount
        let theta' = theta.ToRowMatrix()                                             
        [0..m-1] |> List.map (fun i -> (((theta' * trainingData.[i,0..1]) |> Seq.exactlyOne) - yVals.[i] ))
    

    编辑:
    我的猜测是 mapRows 希望所有内容都具有相同的形状,并且您的输出向量不同。所以如果你想坚持 Vector 类型,这只会枚举索引行:

    tData.EnumerateRowsIndexed() |&gt; Seq.map (fun (i,r) -&gt; (theta' * r) - yVals.[i])
    如果您更喜欢通过管道传输它,也可以使用Matrix.toRowSeqi,然后取回一个矩阵:

    tData 
        |> Matrix.toRowSeqi 
        |> Seq.map (fun (i,x) -> (theta' * x) - yVals.[i]) 
        |> DenseMatrix.ofRowSeq
    

    【讨论】:

    • 最后一个是钱。这就是我最终实现的,就像翻转魅力一样!
    • 其实我用这个滚动,因为它的平方和:让 SumSquares (theta:Vector) (y:Vector) (trainingData:Matrix) = let theta' = theta.ToRowMatrix() trainingData |> Matrix.toRowSeqi |> Seq.map(fun (i,r) -> vector [ square((theta' * r) - y.[i]) ] ) |> DenseMatrix.ofRowSeq
    • 如果您可以复制我刚刚发布的帖子,我会为您提供答案。
    • 应该没问题,因为它供将来参考,您的评论说明了一切。让我有机会看看Mathnet。您的解决方案非常干净整洁。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-11-25
    • 1970-01-01
    • 2020-08-09
    • 2021-03-27
    • 2010-12-05
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多