Browse Source

LA: F# matrix/vector creation now fully generic (hence all modules also)

optimization-1
Christoph Ruegg 13 years ago
parent
commit
638d055edd
  1. 2
      src/FSharp/FSharp.fsproj
  2. 4
      src/FSharp/Fit.fs
  3. 206
      src/FSharp/LinearAlgebra.Double.Matrix.fs
  4. 110
      src/FSharp/LinearAlgebra.Double.Vector.fs
  5. 305
      src/FSharp/LinearAlgebra.Matrix.fs
  6. 129
      src/FSharp/LinearAlgebra.Vector.fs
  7. 6
      src/FSharpPortable/FSharpPortable.fsproj
  8. 7
      src/FSharpUnitTests/DenseMatrixTests.fs
  9. 11
      src/FSharpUnitTests/DenseVectorTests.fs
  10. 27
      src/FSharpUnitTests/MatrixTests.fs
  11. 5
      src/FSharpUnitTests/SparseMatrixTests.fs
  12. 4
      src/FSharpUnitTests/SparseVectorTests.fs
  13. 29
      src/FSharpUnitTests/VectorTests.fs
  14. 2
      src/Numerics/LinearAlgebra/Builder.cs

2
src/FSharp/FSharp.fsproj

@ -64,8 +64,6 @@
<Compile Include="Distributions.fs" />
<Compile Include="LinearAlgebra.Vector.fs" />
<Compile Include="LinearAlgebra.Matrix.fs" />
<Compile Include="LinearAlgebra.Double.Vector.fs" />
<Compile Include="LinearAlgebra.Double.Matrix.fs" />
<Compile Include="Complex.fsi" />
<Compile Include="Complex.fs" />
<Compile Include="BigIntegerExtensions.fs" />

4
src/FSharp/Fit.fs

@ -31,7 +31,7 @@
namespace MathNet.Numerics
open System
open MathNet.Numerics.LinearAlgebra.Double
open MathNet.Numerics.LinearAlgebra
open MathNet.Numerics.LinearAlgebra.Factorization
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
@ -63,7 +63,7 @@ module Fit =
functions
|> List.map (fun f -> List.init (Array.length x) (fun i -> f x.[i]))
|> DenseMatrix.ofColumnList
|> fun m -> m.QR(QRMethod.Thin).Solve(DenseVector(y)).ToArray()
|> fun m -> m.QR(QRMethod.Thin).Solve(DenseVector.raw y).ToArray()
|> List.ofArray
/// Least-Squares fitting the points (x,y) to an arbitrary linear combination y : x -> p0*f0(x) + p1*f1(x) + ... + pk*fk(x),

206
src/FSharp/LinearAlgebra.Double.Matrix.fs

@ -1,206 +0,0 @@
// <copyright file="LinearAlgebra.Double.Matrix.fs" company="Math.NET">
// Math.NET Numerics, part of the Math.NET Project
// http://numerics.mathdotnet.com
// http://github.com/mathnet/mathnet-numerics
// http://mathnetnumerics.codeplex.com
//
// Copyright (c) 2009-2013 Math.NET
//
// Permission is hereby granted, free of charge, to any person
// obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without
// restriction, including without limitation the rights to use,
// copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the
// Software is furnished to do so, subject to the following
// conditions:
//
// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
// OTHER DEALINGS IN THE SOFTWARE.
// </copyright>
namespace MathNet.Numerics.LinearAlgebra.Double
open MathNet.Numerics.LinearAlgebra
/// A module which implements functional dense vector operations.
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module DenseMatrix =
/// Create a matrix that directly binds to a raw storage array in column-major (column by column) format, without copying.
let inline raw (rows: int) (cols: int) (columnMajor: float[]) = DenseMatrix(rows, cols, columnMajor) :> _ Matrix
/// Create an all-zero matrix with the given dimension.
let inline zeroCreate (rows: int) (cols: int) = DenseMatrix(rows, cols) :> _ Matrix
/// Create a random matrix with the given dimension and value distribution.
let inline randomCreate (rows: int) (cols: int) dist = DenseMatrix.CreateRandom(rows, cols, dist) :> _ Matrix
/// Create a matrix with the given dimension and set all values to x.
let inline create (rows: int) (cols: int) (x: float) = DenseMatrix.Create(rows, cols, x) :> _ Matrix
/// Create a matrix with the given dimension and set all diagonal values to x. All other values are zero.
let inline createDiag (rows: int) (cols: int) (x: float) = DenseMatrix.CreateDiagonal(rows, cols, x) :> _ Matrix
/// Initialize a matrix by calling a construction function for every element.
let inline init (rows: int) (cols: int) (f: int -> int -> float) = DenseMatrix.Create(rows, cols, fun i j -> f i j) :> _ Matrix
/// Initialize a matrix by calling a construction function for every row.
let inline initRows (rows: int) (f: int -> Vector<float>) = DenseMatrix.OfRowVectors(Array.init rows f) :> _ Matrix
/// Initialize a matrix by calling a construction function for every column.
let inline initColumns (cols: int) (f: int -> Vector<float>) = DenseMatrix.OfColumnVectors(Array.init cols f) :> _ Matrix
/// Initialize a matrix by calling a construction function for every diagonal element. All other values are zero.
let inline initDiag (rows: int) (cols: int) (f: int -> float) = DenseMatrix.CreateDiagonal(rows, cols, f) :> _ Matrix
/// Create an identity matrix with the given dimension.
let inline identity (rows: int) (cols: int) = createDiag rows cols 1.0
/// Create a matrix from a 2D array of floating point numbers.
let inline ofArray2 array = DenseMatrix.OfArray(array) :> _ Matrix
/// Create a matrix from a list of row vectors.
let inline ofRows (rows: Vector<float> list) = DenseMatrix.OfRowVectors(Array.ofList rows) :> _ Matrix
/// Create a matrix from a list of row arrays.
let inline ofRowArrays (rows: float[][]) = DenseMatrix.OfRowArrays(rows) :> _ Matrix
/// Create a matrix from a list of float lists. Every list in the master list specifies a row.
let inline ofRowList (rows: float list list) = DenseMatrix.OfRowArrays(rows |> List.map List.toArray |> List.toArray) :> _ Matrix
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a row.
let inline ofRowSeq (rows: #seq<#seq<float>>) = DenseMatrix.OfRowArrays(rows |> Seq.map Seq.toArray |> Seq.toArray) :> _ Matrix
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a row.
let inline ofRowSeq2 (rows: int) (cols: int) (seqOfRows: #seq<seq<float>>) = DenseMatrix.OfRows(rows, cols, seqOfRows) :> _ Matrix
/// Create a matrix from a list of column vectors.
let inline ofColumns (columns: Vector<float> list) = DenseMatrix.OfColumnVectors(Array.ofList columns) :> _ Matrix
/// Create a matrix from a list of column arrays.
let inline ofColumnArrays (columns: float[][]) = DenseMatrix.OfColumnArrays(columns) :> _ Matrix
/// Create a matrix from a list of float lists. Every list in the master list specifies a column.
let inline ofColumnList (columns: float list list) = DenseMatrix.OfColumnArrays(columns |> List.map List.toArray |> List.toArray) :> _ Matrix
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a column.
let inline ofColumnSeq (columns: #seq<#seq<float>>) = DenseMatrix.OfColumnArrays(columns |> Seq.map Seq.toArray |> Seq.toArray) :> _ Matrix
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a column.
let inline ofColumnSeq2 (rows: int) (cols: int) (seqOfCols: #seq<seq<float>>) = DenseMatrix.OfColumns(rows, cols, seqOfCols) :> _ Matrix
/// Create a matrix with a given dimension from an indexed list of row, column, value tuples.
let inline ofListi (rows: int) (cols: int) (indexed: list<int * int * float>) = DenseMatrix.OfIndexed(rows, cols, Seq.ofList indexed) :> _ Matrix
/// Create a matrix with a given dimension from an indexed sequences of row, column, value tuples.
let inline ofSeqi (rows: int) (cols: int) (indexed: #seq<int * int * float>) = DenseMatrix.OfIndexed(rows, cols, indexed) :> _ Matrix
/// Create a square matrix with the vector elements on the diagonal.
let inline ofDiag (v: Vector<float>) = DenseMatrix.OfDiagonalVector(v) :> _ Matrix
/// Create a matrix with the vector elements on the diagonal.
let inline ofDiag2 (rows: int) (cols: int) (v: Vector<float>) = DenseMatrix.OfDiagonalVector(rows, cols, v) :> _ Matrix
/// Create a square matrix with the array elements on the diagonal.
let inline ofDiagArray (array: float array) = DenseMatrix.OfDiagonalArray(array) :> _ Matrix
/// Create a matrix with the array elements on the diagonal.
let inline ofDiagArray2 (rows: int) (cols: int) (array: float array) = DenseMatrix.OfDiagonalArray(rows, cols, array) :> _ Matrix
/// A module which implements functional sparse vector operations.
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module SparseMatrix =
/// Create an all-zero matrix with the given dimension.
let inline zeroCreate (rows: int) (cols: int) = SparseMatrix(rows, cols) :> _ Matrix
/// Create a matrix with the given dimension and set all values to x. Note that a dense matrix would likely be more appropriate.
let inline create (rows: int) (cols: int) (x: float) = SparseMatrix.Create(rows, cols, x) :> _ Matrix
/// Create a matrix with the given dimension and set all diagonal values to x. All other values are zero.
let inline createDiag (rows: int) (cols: int) (x: float) = SparseMatrix.CreateDiagonal(rows, cols, x) :> _ Matrix
/// Initialize a matrix by calling a construction function for every element.
let inline init (rows: int) (cols: int) (f: int -> int -> float) = SparseMatrix.Create(rows, cols, fun n m -> f n m) :> _ Matrix
/// Initialize a matrix by calling a construction function for every row.
let inline initRows (rows: int) (f: int -> Vector<float>) = SparseMatrix.OfRowVectors(Array.init rows f) :> _ Matrix
/// Initialize a matrix by calling a construction function for every column.
let inline initColumns (cols: int) (f: int -> Vector<float>) = SparseMatrix.OfColumnVectors(Array.init cols f) :> _ Matrix
/// Initialize a matrix by calling a construction function for every diagonal element. All other values are zero.
let inline initDiag (rows: int) (cols: int) (f: int -> float) = SparseMatrix.CreateDiagonal(rows, cols, f) :> _ Matrix
/// Create an identity matrix with the given dimension.
let inline identity (rows: int) (cols: int) = createDiag rows cols 1.0
/// Create a matrix from a 2D array of floating point numbers.
let inline ofArray2 array = SparseMatrix.OfArray(array) :> _ Matrix
/// Create a matrix from a list of row vectors.
let inline ofRows (rows: Vector<float> list) = SparseMatrix.OfRowVectors(Array.ofList rows) :> _ Matrix
/// Create a matrix from a list of row arrays.
let inline ofRowArrays (rows: float[][]) = SparseMatrix.OfRowArrays(rows) :> _ Matrix
/// Create a matrix from a list of float lists. Every list in the master list specifies a row.
let inline ofRowList (rows: float list list) = SparseMatrix.OfRowArrays(rows |> List.map List.toArray |> List.toArray) :> _ Matrix
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a row.
let inline ofRowSeq (rows: #seq<#seq<float>>) = SparseMatrix.OfRowArrays(rows |> Seq.map Seq.toArray |> Seq.toArray) :> _ Matrix
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a row.
let inline ofRowSeq2 (rows: int) (cols: int) (seqOfRows: #seq<seq<float>>) = SparseMatrix.OfRows(rows, cols, seqOfRows) :> _ Matrix
/// Create a matrix from a list of column vectors.
let inline ofColumns (columns: Vector<float> list) = SparseMatrix.OfColumnVectors(Array.ofList columns) :> _ Matrix
/// Create a matrix from a list of column arrays.
let inline ofColumnArrays (columns: float[][]) = SparseMatrix.OfColumnArrays(columns) :> _ Matrix
/// Create a matrix from a list of float lists. Every list in the master list specifies a column.
let inline ofColumnList (columns: float list list) = SparseMatrix.OfColumnArrays(columns |> List.map List.toArray |> List.toArray) :> _ Matrix
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a column.
let inline ofColumnSeq (columns: #seq<#seq<float>>) = SparseMatrix.OfColumnArrays(columns |> Seq.map Seq.toArray |> Seq.toArray) :> _ Matrix
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a column.
let inline ofColumnSeq2 (rows: int) (cols: int) (seqOfCols: #seq<seq<float>>) = SparseMatrix.OfColumns(rows, cols, seqOfCols) :> _ Matrix
/// Create a matrix with a given dimension from an indexed list of row, column, value tuples.
let inline ofListi (rows: int) (cols: int) (indexed: list<int * int * float>) = SparseMatrix.OfIndexed(rows, cols, Seq.ofList indexed) :> _ Matrix
/// Create a matrix with a given dimension from an indexed sequences of row, column, value tuples.
let inline ofSeqi (rows: int) (cols: int) (indexed: #seq<int * int * float>) = SparseMatrix.OfIndexed(rows, cols, indexed) :> _ Matrix
/// Create a square matrix with the vector elements on the diagonal.
let inline ofDiag (v: Vector<float>) = SparseMatrix.OfDiagonalVector(v) :> _ Matrix
/// Create a matrix with the vector elements on the diagonal.
let inline ofDiag2 (rows: int) (cols: int) (v: Vector<float>) = SparseMatrix.OfDiagonalVector(rows, cols, v) :> _ Matrix
/// Create a square matrix with the array elements on the diagonal.
let inline ofDiagArray (array: float array) = SparseMatrix.OfDiagonalArray(array) :> _ Matrix
/// Create a matrix with the array elements on the diagonal.
let inline ofDiagArray2 (rows: int) (cols: int) (array: float array) = SparseMatrix.OfDiagonalArray(rows, cols, array) :> _ Matrix
/// A module which implements some F# utility functions.
[<AutoOpen>]
module MatrixUtility =
/// Construct a dense matrix from a nested list of floating point numbers.
let inline matrix (lst: list<list<float>>) = DenseMatrix.ofRowList lst

110
src/FSharp/LinearAlgebra.Double.Vector.fs

@ -1,110 +0,0 @@
// <copyright file="LinearAlgebra.Double.Vector.fs" company="Math.NET">
// Math.NET Numerics, part of the Math.NET Project
// http://numerics.mathdotnet.com
// http://github.com/mathnet/mathnet-numerics
// http://mathnetnumerics.codeplex.com
//
// Copyright (c) 2009-2013 Math.NET
//
// Permission is hereby granted, free of charge, to any person
// obtaining a copy of this software and associated documentation
// files (the "Software"), to deal in the Software without
// restriction, including without limitation the rights to use,
// copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the
// Software is furnished to do so, subject to the following
// conditions:
//
// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
// OTHER DEALINGS IN THE SOFTWARE.
// </copyright>
namespace MathNet.Numerics.LinearAlgebra.Double
open MathNet.Numerics.LinearAlgebra
/// A module which implements functional dense vector operations.
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module DenseVector =
/// Create a vector that directly binds to a raw storage array, without copying.
let inline raw (raw: float[]) = DenseVector(raw) :> _ Vector
/// Initialize an all-zero vector with the given dimension.
let inline zeroCreate (n: int) = DenseVector(n) :> _ Vector
/// Initialize a random vector with the given dimension and distribution.
let inline randomCreate (n: int) dist = DenseVector.CreateRandom(n, dist) :> _ Vector
/// Initialize an x-valued vector with the given dimension.
let inline create (n: int) (x: float) = DenseVector.Create(n, x) :> _ Vector
/// Initialize a vector by calling a construction function for every element.
let inline init (n: int) (f: int -> float) = DenseVector.Create(n, f) :> _ Vector
/// Create a vector from a float array (by copying - use raw instead if no copy is needed).
let inline ofArray (fl: float array) = DenseVector(Array.copy fl) :> _ Vector
/// Create a vector from a float list.
let inline ofList (fl: float list) = DenseVector(Array.ofList fl) :> _ Vector
/// Create a vector from a float sequence.
let inline ofSeq (fs: #seq<float>) = DenseVector.OfEnumerable(fs) :> _ Vector
/// Create a vector with a given dimension from an indexed list of index, value pairs.
let inline ofListi (n: int) (fl: list<int * float>) = DenseVector.OfIndexedEnumerable(n, Seq.ofList fl) :> _ Vector
/// Create a vector with a given dimension from an indexed sequences of index, value pairs.
let inline ofSeqi (n: int) (fs: #seq<int * float>) = DenseVector.OfIndexedEnumerable(n, fs) :> _ Vector
/// Create a vector with integer entries in the given range.
let inline range (start: int) (step: int) (stop: int) = raw [| for i in start..step..stop -> float i |]
/// Create a vector with evenly spaced entries: e.g. rangef -1.0 0.5 1.0 = [-1.0 -0.5 0.0 0.5 1.0]
let inline rangef (start: float) (step: float) (stop: float) = raw [| start..step..stop |]
/// A module which implements functional sparse vector operations.
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module SparseVector =
/// Initialize an all-zero vector with the given dimension.
let inline zeroCreate (n: int) = SparseVector(n) :> _ Vector
/// Initialize an x-valued vector with the given dimension.
let inline create (n: int) (x: float) = SparseVector.Create(n, x) :> _ Vector
/// Initialize a vector by calling a construction function for every element.
let inline init (n: int) (f: int -> float) = SparseVector.Create(n, f) :> _ Vector
/// Create a sparse vector from a float array.
let inline ofArray (fl: float array) = SparseVector.OfEnumerable(Seq.ofArray fl) :> _ Vector
/// Create a sparse vector from a float list.
let inline ofList (fl: float list) = SparseVector.OfEnumerable(Seq.ofList fl) :> _ Vector
/// Create a sparse vector from a float sequence.
let inline ofSeq (fs: #seq<float>) = SparseVector.OfEnumerable(fs) :> _ Vector
/// Create a sparse vector with a given dimension from an indexed list of index, value pairs.
let inline ofListi (n: int) (fl: list<int * float>) = SparseVector.OfIndexedEnumerable(n, Seq.ofList fl) :> _ Vector
/// Create a sparse vector with a given dimension from an indexed sequence of index, value pairs.
let inline ofSeqi (n: int) (fs: #seq<int * float>) = SparseVector.OfIndexedEnumerable(n, fs) :> _ Vector
/// A module which implements some F# utility functions.
[<AutoOpen>]
module VectorUtility =
/// Construct a dense vector from a list of floating point numbers.
let inline vector (lst: list<float>) = DenseVector.ofList lst

305
src/FSharp/LinearAlgebra.Matrix.fs

@ -30,64 +30,8 @@
namespace MathNet.Numerics.LinearAlgebra
/// Module that contains implementation of useful F#-specific extension members for generic matrices
[<AutoOpen>]
module MatrixExtensions =
// A type extension for the generic matrix type that
// adds the 'GetSlice' method to allow m.[r1 .. r2, c1 .. c2] syntax
type MathNet.Numerics.LinearAlgebra.
Matrix<'T when 'T : struct and 'T : (new : unit -> 'T)
and 'T :> System.IEquatable<'T> and 'T :> System.IFormattable
and 'T :> System.ValueType> with
/// Gets a submatrix using a specified column range and
/// row range (all indices are optional)
/// This method can be used via the x.[r1 .. r2, c1 .. c2 ] syntax
member x.GetSlice(rstart, rfinish, cstart, cfinish) =
let cstart = defaultArg cstart 0
let rstart = defaultArg rstart 0
let cfinish = defaultArg cfinish (x.ColumnCount - 1)
let rfinish = defaultArg rfinish (x.RowCount - 1)
x.SubMatrix(rstart, rfinish - rstart + 1, cstart, cfinish - cstart + 1)
/// Sets a submatrix using a specified column range and
/// row range (all indices are optional)
/// This method can be used via the x.[r1 .. r2, c1 .. c2 ] <- m syntax
member x.SetSlice(rstart, rfinish, cstart, cfinish, values) =
let cstart = defaultArg cstart 0
let rstart = defaultArg rstart 0
let cfinish = defaultArg cfinish (x.ColumnCount - 1)
let rfinish = defaultArg rfinish (x.RowCount - 1)
x.SetSubMatrix(rstart, rfinish - rstart + 1, cstart, cfinish - cstart + 1, values)
/// Gets a row subvector using a specified row index and column range.
/// This method can be used via the x.[r, c1 .. c2] syntax (F#3.1)
member x.GetSlice(r, cstart, cfinish) =
let cstart = defaultArg cstart 0
let cfinish = defaultArg cfinish (x.ColumnCount - 1)
x.Row(r, cstart, cfinish - cstart + 1)
/// Gets a column subvector using a specified row index and column range.
/// This method can be used via the x.[r1 .. r2, c] syntax (F#3.1)
member x.GetSlice(rstart, rfinish, c) =
let rstart = defaultArg rstart 0
let rfinish = defaultArg rfinish (x.RowCount - 1)
x.Column(c, rstart, rfinish - rstart + 1)
/// Sets a row subvector using a specified row index and column range.
/// This method can be used via the x.[r, c1 .. c2] <- v syntax (F#3.1)
member x.SetSlice(r, cstart, cfinish, values) =
let cstart = defaultArg cstart 0
let cfinish = defaultArg cfinish (x.ColumnCount - 1)
x.SetRow(r, cstart, cfinish - cstart + 1, values)
/// Sets a column subvector using a specified row index and column range.
/// This method can be used via the x.[r1 .. r2, c] <- v syntax (F#3.1)
member x.SetSlice(rstart, rfinish, c, values) =
let rstart = defaultArg rstart 0
let rfinish = defaultArg rfinish (x.RowCount - 1)
x.SetColumn(c, rstart, rfinish - rstart + 1, values)
open System
open MathNet.Numerics.LinearAlgebra
/// A module which implements functional matrix operations.
@ -398,4 +342,247 @@ module Matrix =
/// Returns the sum of the results generated by applying a position dependent function to each row of the matrix.
let inline sumRowsBy f (A: #Matrix<_>) =
A.EnumerateRowsIndexed() |> Seq.map (fun (i,row) -> f i row) |> Seq.reduce (+)
A.EnumerateRowsIndexed() |> Seq.map (fun (i,row) -> f i row) |> Seq.reduce (+)
// Workaround an issue when passing generic arguments to a params-array. Get rid of this once we're on F# > 3.1.
type internal ParamsInvokeWorkaround<'T when 'T : (new: unit -> 'T) and 'T: struct and 'T :> ValueType and 'T :> IEquatable<'T> and 'T :> IFormattable> private ()=
static let build = Matrix<'T>.Build
static let dr = Delegate.CreateDelegate(typeof<Func<'T[][],Matrix<'T>>>, build, typeof<Builder<'T>>.GetMethod("DenseMatrixOfRowArrays")) :?> Func<'T[][],Matrix<'T>>
static let dc = Delegate.CreateDelegate(typeof<Func<'T[][],Matrix<'T>>>, build, typeof<Builder<'T>>.GetMethod("DenseMatrixOfColumnArrays")) :?> Func<'T[][],Matrix<'T>>
static let sr = Delegate.CreateDelegate(typeof<Func<'T[][],Matrix<'T>>>, build, typeof<Builder<'T>>.GetMethod("SparseMatrixOfRowArrays")) :?> Func<'T[][],Matrix<'T>>
static let sc = Delegate.CreateDelegate(typeof<Func<'T[][],Matrix<'T>>>, build, typeof<Builder<'T>>.GetMethod("SparseMatrixOfColumnArrays")) :?> Func<'T[][],Matrix<'T>>
static member DenseMatrixOfRowArrays(array) = dr.Invoke array
static member DenseMatrixOfColumnArrays(array) = dc.Invoke array
static member SparseMatrixOfRowArrays(array) = sr.Invoke array
static member SparseMatrixOfColumnArrays(array) = sc.Invoke array
/// A module which helps constructing generic dense matrices.
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module DenseMatrix =
/// Create a matrix that directly binds to a raw storage array in column-major (column by column) format, without copying.
let inline raw (rows: int) (cols: int) (columnMajor: 'T[]) = Matrix<'T>.Build.DenseMatrix(rows, cols, columnMajor)
/// Create an all-zero matrix with the given dimension.
let inline zeroCreate (rows: int) (cols: int) = Matrix<'T>.Build.DenseMatrix(rows, cols)
/// Create a random matrix with the given dimension and value distribution.
let inline randomCreate (rows: int) (cols: int) dist = Matrix<'T>.Build.DenseMatrixRandom(rows, cols, dist)
/// Create a matrix with the given dimension and set all values to x.
let inline create (rows: int) (cols: int) (x: 'T) = Matrix<'T>.Build.DenseMatrix(rows, cols, x)
/// Create a matrix with the given dimension and set all diagonal values to x. All other values are zero.
let inline createDiag (rows: int) (cols: int) (x: 'T) = Matrix<'T>.Build.DenseMatrixDiagonal(rows, cols, x)
/// Initialize a matrix by calling a construction function for every element.
let inline init (rows: int) (cols: int) (f: int -> int -> 'T) = Matrix<'T>.Build.DenseMatrix(rows, cols, fun i j -> f i j)
/// Initialize a matrix by calling a construction function for every row.
let inline initRows (rows: int) (f: int -> Vector<'T>) = Matrix<'T>.Build.DenseMatrixOfRowVectors(Array.init rows f)
/// Initialize a matrix by calling a construction function for every column.
let inline initColumns (cols: int) (f: int -> Vector<'T>) = Matrix<'T>.Build.DenseMatrixOfColumnVectors(Array.init cols f)
/// Initialize a matrix by calling a construction function for every diagonal element. All other values are zero.
let inline initDiag (rows: int) (cols: int) (f: int -> 'T) = Matrix<'T>.Build.DenseMatrixDiagonal(rows, cols, f)
/// Create an identity matrix with the given dimension.
let inline identity (rows: int) (cols: int) = createDiag rows cols Matrix<'T>.Build.One
/// Create a matrix from a 2D array of floating point numbers.
let inline ofArray2 array = Matrix<'T>.Build.DenseMatrixOfArray(array)
/// Create a matrix from a list of row vectors.
let inline ofRows (rows: Vector<'T> list) = Matrix<'T>.Build.DenseMatrixOfRowVectors(Array.ofList rows)
/// Create a matrix from a list of row arrays.
let ofRowArrays (rows: 'T[][]) = ParamsInvokeWorkaround<'T>.DenseMatrixOfRowArrays(rows)
/// Create a matrix from a list of float lists. Every list in the master list specifies a row.
let inline ofRowList (rows: 'T list list) = rows |> List.map List.toArray |> List.toArray |> ofRowArrays
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a row.
let inline ofRowSeq (rows: #seq<#seq<'T>>) = rows |> Seq.map Seq.toArray |> Seq.toArray |> ofRowArrays
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a row.
let inline ofRowSeq2 (rows: int) (cols: int) (seqOfRows: #seq<seq<'T>>) = Matrix<'T>.Build.DenseMatrixOfRows(rows, cols, seqOfRows)
/// Create a matrix from a list of column vectors.
let inline ofColumns (columns: Vector<'T> list) = Matrix<'T>.Build.DenseMatrixOfColumnVectors(Array.ofList columns)
/// Create a matrix from a list of column arrays.
let ofColumnArrays (columns: 'T[][]) = ParamsInvokeWorkaround<'T>.DenseMatrixOfColumnArrays(columns)
/// Create a matrix from a list of float lists. Every list in the master list specifies a column.
let inline ofColumnList (columns: 'T list list) = columns |> List.map List.toArray |> List.toArray |> ofColumnArrays
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a column.
let inline ofColumnSeq (columns: #seq<#seq<'T>>) = columns |> Seq.map Seq.toArray |> Seq.toArray |> ofColumnArrays
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a column.
let inline ofColumnSeq2 (rows: int) (cols: int) (seqOfCols: #seq<seq<'T>>) = Matrix<'T>.Build.DenseMatrixOfColumns(rows, cols, seqOfCols)
/// Create a matrix with a given dimension from an indexed list of row, column, value tuples.
let inline ofListi (rows: int) (cols: int) (indexed: list<int * int * 'T>) = Matrix<'T>.Build.DenseMatrixOfIndexed(rows, cols, Seq.ofList indexed)
/// Create a matrix with a given dimension from an indexed sequences of row, column, value tuples.
let inline ofSeqi (rows: int) (cols: int) (indexed: #seq<int * int * 'T>) = Matrix<'T>.Build.DenseMatrixOfIndexed(rows, cols, indexed)
/// Create a square matrix with the vector elements on the diagonal.
let inline ofDiag (v: Vector<'T>) = Matrix<'T>.Build.DenseMatrixOfDiagonalVector(v)
/// Create a matrix with the vector elements on the diagonal.
let inline ofDiag2 (rows: int) (cols: int) (v: Vector<'T>) = Matrix<'T>.Build.DenseMatrixOfDiagonalVector(rows, cols, v)
/// Create a square matrix with the array elements on the diagonal.
let inline ofDiagArray (array: 'T array) = Matrix<'T>.Build.DenseMatrixOfDiagonalArray(array)
/// Create a matrix with the array elements on the diagonal.
let inline ofDiagArray2 (rows: int) (cols: int) (array: 'T array) = Matrix<'T>.Build.DenseMatrixOfDiagonalArray(rows, cols, array)
/// A module which helps constructing generic sparse matrices.
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module SparseMatrix =
/// Create an all-zero matrix with the given dimension.
let inline zeroCreate (rows: int) (cols: int) = Matrix<'T>.Build.SparseMatrix(rows, cols)
/// Create a matrix with the given dimension and set all values to x. Note that a dense matrix would likely be more appropriate.
let inline create (rows: int) (cols: int) (x: 'T) = Matrix<'T>.Build.SparseMatrix(rows, cols, x)
/// Create a matrix with the given dimension and set all diagonal values to x. All other values are zero.
let inline createDiag (rows: int) (cols: int) (x: 'T) = Matrix<'T>.Build.SparseMatrixDiagonal(rows, cols, x)
/// Initialize a matrix by calling a construction function for every element.
let inline init (rows: int) (cols: int) (f: int -> int -> 'T) = Matrix<'T>.Build.SparseMatrix(rows, cols, fun n m -> f n m)
/// Initialize a matrix by calling a construction function for every row.
let inline initRows (rows: int) (f: int -> Vector<'T>) = Matrix<'T>.Build.SparseMatrixOfRowVectors(Array.init rows f)
/// Initialize a matrix by calling a construction function for every column.
let inline initColumns (cols: int) (f: int -> Vector<'T>) = Matrix<'T>.Build.SparseMatrixOfColumnVectors(Array.init cols f)
/// Initialize a matrix by calling a construction function for every diagonal element. All other values are zero.
let inline initDiag (rows: int) (cols: int) (f: int -> 'T) = Matrix<'T>.Build.SparseMatrixDiagonal(rows, cols, f)
/// Create an identity matrix with the given dimension.
let inline identity (rows: int) (cols: int) = createDiag rows cols Matrix<'T>.Build.One
/// Create a matrix from a 2D array of floating point numbers.
let inline ofArray2 array = Matrix<'T>.Build.SparseMatrixOfArray(array)
/// Create a matrix from a list of row vectors.
let inline ofRows (rows: Vector<'T> list) = Matrix<'T>.Build.SparseMatrixOfRowVectors(Array.ofList rows)
/// Create a matrix from a list of row arrays.
let ofRowArrays (rows: 'T[][]) = ParamsInvokeWorkaround<'T>.SparseMatrixOfRowArrays(rows)
/// Create a matrix from a list of float lists. Every list in the master list specifies a row.
let inline ofRowList (rows: 'T list list) = rows |> List.map List.toArray |> List.toArray |> ofRowArrays
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a row.
let inline ofRowSeq (rows: #seq<#seq<'T>>) = rows |> Seq.map Seq.toArray |> Seq.toArray |> ofRowArrays
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a row.
let inline ofRowSeq2 (rows: int) (cols: int) (seqOfRows: #seq<seq<'T>>) = Matrix<'T>.Build.SparseMatrixOfRows(rows, cols, seqOfRows)
/// Create a matrix from a list of column vectors.
let inline ofColumns (columns: Vector<'T> list) = Matrix<'T>.Build.SparseMatrixOfColumnVectors(Array.ofList columns)
/// Create a matrix from a list of column arrays.
let ofColumnArrays (columns: 'T[][]) = ParamsInvokeWorkaround<'T>.SparseMatrixOfColumnArrays(columns)
/// Create a matrix from a list of float lists. Every list in the master list specifies a column.
let inline ofColumnList (columns: 'T list list) = columns |> List.map List.toArray |> List.toArray |> ofColumnArrays
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a column.
let inline ofColumnSeq (columns: #seq<#seq<'T>>) = columns |> Seq.map Seq.toArray |> Seq.toArray |> ofColumnArrays
/// Create a matrix from a list of sequences. Every sequence in the master sequence specifies a column.
let inline ofColumnSeq2 (rows: int) (cols: int) (seqOfCols: #seq<seq<'T>>) = Matrix<'T>.Build.SparseMatrixOfColumns(rows, cols, seqOfCols)
/// Create a matrix with a given dimension from an indexed list of row, column, value tuples.
let inline ofListi (rows: int) (cols: int) (indexed: list<int * int * 'T>) = Matrix<'T>.Build.SparseMatrixOfIndexed(rows, cols, Seq.ofList indexed)
/// Create a matrix with a given dimension from an indexed sequences of row, column, value tuples.
let inline ofSeqi (rows: int) (cols: int) (indexed: #seq<int * int * 'T>) = Matrix<'T>.Build.SparseMatrixOfIndexed(rows, cols, indexed)
/// Create a square matrix with the vector elements on the diagonal.
let inline ofDiag (v: Vector<'T>) = Matrix<'T>.Build.SparseMatrixOfDiagonalVector(v)
/// Create a matrix with the vector elements on the diagonal.
let inline ofDiag2 (rows: int) (cols: int) (v: Vector<'T>) = Matrix<'T>.Build.SparseMatrixOfDiagonalVector(rows, cols, v)
/// Create a square matrix with the array elements on the diagonal.
let inline ofDiagArray (array: 'T array) = Matrix<'T>.Build.SparseMatrixOfDiagonalArray(array)
/// Create a matrix with the array elements on the diagonal.
let inline ofDiagArray2 (rows: int) (cols: int) (array: 'T array) = Matrix<'T>.Build.SparseMatrixOfDiagonalArray(rows, cols, array)
/// Module that contains implementation of useful F#-specific extension members for generic matrices
[<AutoOpen>]
module MatrixExtensions =
/// Construct a dense matrix from a nested list of numbers.
let inline matrix (lst: list<list<'T>>) = DenseMatrix.ofRowList lst
// A type extension for the generic matrix type that
// adds the 'GetSlice' method to allow m.[r1 .. r2, c1 .. c2] syntax
type MathNet.Numerics.LinearAlgebra.
Matrix<'T when 'T : struct and 'T : (new : unit -> 'T)
and 'T :> System.IEquatable<'T> and 'T :> System.IFormattable
and 'T :> System.ValueType> with
/// Gets a submatrix using a specified column range and
/// row range (all indices are optional)
/// This method can be used via the x.[r1 .. r2, c1 .. c2 ] syntax
member x.GetSlice(rstart, rfinish, cstart, cfinish) =
let cstart = defaultArg cstart 0
let rstart = defaultArg rstart 0
let cfinish = defaultArg cfinish (x.ColumnCount - 1)
let rfinish = defaultArg rfinish (x.RowCount - 1)
x.SubMatrix(rstart, rfinish - rstart + 1, cstart, cfinish - cstart + 1)
/// Sets a submatrix using a specified column range and
/// row range (all indices are optional)
/// This method can be used via the x.[r1 .. r2, c1 .. c2 ] <- m syntax
member x.SetSlice(rstart, rfinish, cstart, cfinish, values) =
let cstart = defaultArg cstart 0
let rstart = defaultArg rstart 0
let cfinish = defaultArg cfinish (x.ColumnCount - 1)
let rfinish = defaultArg rfinish (x.RowCount - 1)
x.SetSubMatrix(rstart, rfinish - rstart + 1, cstart, cfinish - cstart + 1, values)
/// Gets a row subvector using a specified row index and column range.
/// This method can be used via the x.[r, c1 .. c2] syntax (F#3.1)
member x.GetSlice(r, cstart, cfinish) =
let cstart = defaultArg cstart 0
let cfinish = defaultArg cfinish (x.ColumnCount - 1)
x.Row(r, cstart, cfinish - cstart + 1)
/// Gets a column subvector using a specified row index and column range.
/// This method can be used via the x.[r1 .. r2, c] syntax (F#3.1)
member x.GetSlice(rstart, rfinish, c) =
let rstart = defaultArg rstart 0
let rfinish = defaultArg rfinish (x.RowCount - 1)
x.Column(c, rstart, rfinish - rstart + 1)
/// Sets a row subvector using a specified row index and column range.
/// This method can be used via the x.[r, c1 .. c2] <- v syntax (F#3.1)
member x.SetSlice(r, cstart, cfinish, values) =
let cstart = defaultArg cstart 0
let cfinish = defaultArg cfinish (x.ColumnCount - 1)
x.SetRow(r, cstart, cfinish - cstart + 1, values)
/// Sets a column subvector using a specified row index and column range.
/// This method can be used via the x.[r1 .. r2, c] <- v syntax (F#3.1)
member x.SetSlice(rstart, rfinish, c, values) =
let rstart = defaultArg rstart 0
let rfinish = defaultArg rfinish (x.RowCount - 1)
x.SetColumn(c, rstart, rfinish - rstart + 1, values)

129
src/FSharp/LinearAlgebra.Vector.fs

@ -30,33 +30,6 @@
namespace MathNet.Numerics.LinearAlgebra
/// Module that contains implementation of useful F#-specific extension members for generic vectors
[<AutoOpen>]
module VectorExtensions =
// A type extension for the generic vector type that
// adds the 'GetSlice' method to allow vec.[a .. b] syntax
type MathNet.Numerics.LinearAlgebra.
Vector<'T when 'T : struct and 'T : (new : unit -> 'T)
and 'T :> System.IEquatable<'T> and 'T :> System.IFormattable
and 'T :> System.ValueType> with
/// Gets a slice of a vector starting at a specified index
/// and ending at a specified index (both indices are optional)
/// This method can be used via the x.[start .. finish] syntax
member x.GetSlice(start, finish) =
let start = defaultArg start 0
let finish = defaultArg finish (x.Count - 1)
x.SubVector(start, finish - start + 1)
/// Sets a slice of a vector starting at a specified index
/// and ending at a specified index (both indices are optional)
/// This method can be used via the x.[start .. finish] <- v syntax
member x.SetSlice(start, finish, values) =
let start = defaultArg start 0
let finish = defaultArg finish (x.Count - 1)
x.SetSubVector(start, finish - start + 1, values)
/// A module which implements functional vector operations.
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
@ -241,3 +214,105 @@ module Vector =
/// In place vector subtraction.
let inline subInPlace (v: #Vector<_>) (w: #Vector<_>) = v.Subtract(w, v)
/// A module which helps constructing generic dense vectors.
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module DenseVector =
/// Create a vector that directly binds to a raw storage array, without copying.
let inline raw (raw: 'T[]) = Vector<'T>.Build.DenseVector(raw)
/// Initialize an all-zero vector with the given dimension.
let inline zeroCreate (n: int) = Vector<'T>.Build.DenseVector(n)
/// Initialize a random vector with the given dimension and distribution.
let inline randomCreate (n: int) dist = Vector<'T>.Build.DenseVectorRandom(n, dist)
/// Initialize an x-valued vector with the given dimension.
let inline create (n: int) (x: 'T) = Vector<'T>.Build.DenseVector(n, x)
/// Initialize a vector by calling a construction function for every element.
let inline init (n: int) (f: int -> 'T) = Vector<'T>.Build.DenseVector(n, f)
/// Create a vector from a float array (by copying - use raw instead if no copy is needed).
let inline ofArray (fl: 'T array) = Vector<'T>.Build.DenseVector(Array.copy fl)
/// Create a vector from a float list.
let inline ofList (fl: 'T list) = Vector<'T>.Build.DenseVector(Array.ofList fl)
/// Create a vector from a float sequence.
let inline ofSeq (fs: #seq<'T>) = Vector<'T>.Build.DenseVectorOfEnumerable(fs)
/// Create a vector with a given dimension from an indexed list of index, value pairs.
let inline ofListi (n: int) (fl: list<int * 'T>) = Vector<'T>.Build.DenseVectorOfIndexed(n, Seq.ofList fl)
/// Create a vector with a given dimension from an indexed sequences of index, value pairs.
let inline ofSeqi (n: int) (fs: #seq<int * 'T>) = Vector<'T>.Build.DenseVectorOfIndexed(n, fs)
/// Create a vector with integer entries in the given range.
let inline range (start: int) (step: int) (stop: int) = raw [| for i in start..step..stop -> float i |]
/// Create a vector with evenly spaced entries: e.g. rangef -1.0 0.5 1.0 = [-1.0 -0.5 0.0 0.5 1.0]
let inline rangef (start: float) (step: float) (stop: float) = raw [| start..step..stop |]
/// A module which helps constructing generic sparse vectors.
[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module SparseVector =
/// Initialize an all-zero vector with the given dimension.
let inline zeroCreate (n: int) = Vector<'T>.Build.SparseVector(n)
/// Initialize an x-valued vector with the given dimension.
let inline create (n: int) (x: 'T) = Vector<'T>.Build.SparseVector(n, x)
/// Initialize a vector by calling a construction function for every element.
let inline init (n: int) (f: int -> 'T) = Vector<'T>.Build.SparseVector(n, f)
/// Create a sparse vector from a float array.
let inline ofArray (fl: 'T array) = Vector<'T>.Build.SparseVectorOfEnumerable(Seq.ofArray fl)
/// Create a sparse vector from a float list.
let inline ofList (fl: 'T list) = Vector<'T>.Build.SparseVectorOfEnumerable(Seq.ofList fl)
/// Create a sparse vector from a float sequence.
let inline ofSeq (fs: #seq<'T>) = Vector<'T>.Build.SparseVectorOfEnumerable(fs)
/// Create a sparse vector with a given dimension from an indexed list of index, value pairs.
let inline ofListi (n: int) (fl: list<int * 'T>) = Vector<'T>.Build.SparseVectorOfIndexed(n, Seq.ofList fl)
/// Create a sparse vector with a given dimension from an indexed sequence of index, value pairs.
let inline ofSeqi (n: int) (fs: #seq<int * 'T>) = Vector<'T>.Build.SparseVectorOfIndexed(n, fs)
/// Module that contains implementation of useful F#-specific extension members for generic vectors
[<AutoOpen>]
module VectorExtensions =
/// Construct a dense vector from a list of floating point numbers.
let inline vector (lst: list<'T>) = DenseVector.ofList lst
// A type extension for the generic vector type that
// adds the 'GetSlice' method to allow vec.[a .. b] syntax
type MathNet.Numerics.LinearAlgebra.
Vector<'T when 'T : struct and 'T : (new : unit -> 'T)
and 'T :> System.IEquatable<'T> and 'T :> System.IFormattable
and 'T :> System.ValueType> with
/// Gets a slice of a vector starting at a specified index
/// and ending at a specified index (both indices are optional)
/// This method can be used via the x.[start .. finish] syntax
member x.GetSlice(start, finish) =
let start = defaultArg start 0
let finish = defaultArg finish (x.Count - 1)
x.SubVector(start, finish - start + 1)
/// Sets a slice of a vector starting at a specified index
/// and ending at a specified index (both indices are optional)
/// This method can be used via the x.[start .. finish] <- v syntax
member x.SetSlice(start, finish, values) =
let start = defaultArg start 0
let finish = defaultArg finish (x.Count - 1)
x.SetSubVector(start, finish - start + 1, values)

6
src/FSharpPortable/FSharpPortable.fsproj

@ -56,12 +56,6 @@
<Compile Include="..\FSharp\LinearAlgebra.Vector.fs">
<Link>LinearAlgebra.Vector.fs</Link>
</Compile>
<Compile Include="..\FSharp\LinearAlgebra.Double.Matrix.fs">
<Link>LinearAlgebra.Double.Matrix.fs</Link>
</Compile>
<Compile Include="..\FSharp\LinearAlgebra.Double.Vector.fs">
<Link>LinearAlgebra.Double.Vector.fs</Link>
</Compile>
<Compile Include="..\FSharp\Complex.fsi">
<Link>Complex.fsi</Link>
</Compile>

7
src/FSharpUnitTests/DenseMatrixTests.fs

@ -3,7 +3,6 @@
open NUnit.Framework
open FsUnit
open MathNet.Numerics.LinearAlgebra
open MathNet.Numerics.LinearAlgebra.Double
open MathNet.Numerics.Distributions
open MathNet.Numerics.Statistics
@ -25,7 +24,7 @@ module DenseMatrixTests =
[<Test>]
let ``DenseMatrix.randomCreate`` () =
let m = DenseMatrix.randomCreate 100 120 (Normal.WithMeanStdDev(100.0,0.1))
(m :?> DenseMatrix).Values |> ArrayStatistics.Mean |> should (equalWithin 10.0) 100.0
(m :?> Double.DenseMatrix).Values |> ArrayStatistics.Mean |> should (equalWithin 10.0) 100.0
m.RowCount |> should equal 100
m.ColumnCount |> should equal 120
@ -80,11 +79,11 @@ module DenseMatrixTests =
[<Test>]
let ``DenseMatrix.createDiag`` () =
DenseMatrix.createDiag 100 100 2.0 |> should equal (2.0 * (DenseMatrix.Identity 100))
DenseMatrix.createDiag 100 100 2.0 |> should equal (2.0 * (DenseMatrix.identity 100 100))
[<Test>]
let ``DenseMatrix.ofDiag`` () =
DenseMatrix.ofDiag (DenseVector.Create(100, fun i -> 2.0)) |> should equal (2.0 * (DenseMatrix.Identity 100))
DenseMatrix.ofDiag (DenseVector.init 100 (fun i -> 2.0)) |> should equal (2.0 * (DenseMatrix.identity 100 100))
[<Test>]
let ``DenseMatrix.initRow`` () =

11
src/FSharpUnitTests/DenseVectorTests.fs

@ -3,7 +3,6 @@
open NUnit.Framework
open FsUnit
open MathNet.Numerics.LinearAlgebra
open MathNet.Numerics.LinearAlgebra.Double
open MathNet.Numerics.Distributions
open MathNet.Numerics.Statistics
@ -11,10 +10,10 @@ open MathNet.Numerics.Statistics
module DenseVectorTests =
/// A small uniform vector.
let smallv = DenseVector.Create(5, fun i -> 0.3)
let smallv = Double.DenseVector.Create(5, fun i -> 0.3)
/// A large vector with increasingly large entries
let largev = new DenseVector( Array.init 100 (fun i -> float i / 100.0) )
let largev = new Double.DenseVector( Array.init 100 (fun i -> float i / 100.0) )
[<Test>]
let ``DenseVector.zeroCreate`` () =
@ -23,7 +22,7 @@ module DenseVectorTests =
[<Test>]
let ``DenseVector.randomCreate`` () =
let m = DenseVector.randomCreate 100 (Normal.WithMeanStdDev(100.0,0.1))
(m :?> DenseVector).Values |> ArrayStatistics.Mean |> should (equalWithin 10.0) 100.0
(m :?> Double.DenseVector).Values |> ArrayStatistics.Mean |> should (equalWithin 10.0) 100.0
m.Count |> should equal 100
[<Test>]
@ -53,8 +52,8 @@ module DenseVectorTests =
[<Test>]
let ``DenseVector.rangef`` () =
DenseVector.rangef 0.0 0.01 0.99 |> should equal (new DenseVector( [| for i in 0 .. 99 -> 0.01 * float i |] ) )
DenseVector.rangef 0.0 0.01 0.99 |> should equal (DenseVector.raw [| for i in 0 .. 99 -> 0.01 * float i |])
[<Test>]
let ``DenseVector.range`` () =
DenseVector.range 0 1 99 |> should equal (new DenseVector( [| for i in 0 .. 99 -> float i |] ) )
DenseVector.range 0 1 99 |> should equal (DenseVector.raw [| for i in 0 .. 99 -> float i |])

27
src/FSharpUnitTests/MatrixTests.fs

@ -3,7 +3,6 @@
open NUnit.Framework
open FsUnit
open MathNet.Numerics.LinearAlgebra
open MathNet.Numerics.LinearAlgebra.Double
/// Unit tests for the matrix type.
module MatrixTests =
@ -24,27 +23,27 @@ module MatrixTests =
let ``Matrix.GetSlice`` () =
largeM.[*,*] |> should equal largeM
largeM.[0..99,0..99] |> should equal largeM
largeM.[1..2,1..2] |> should equal (DenseMatrix(2,2,[|101.;201.;102.;202.|]))
largeM.[98..,98..] |> should equal (DenseMatrix(2,2,[|9898.;9998.;9899.;9999.|]))
largeM.[..1,..1] |> should equal (DenseMatrix(2,2,[|0.;100.;1.;101.|]))
largeM.[1..2,1..2] |> should equal (DenseMatrix.raw 2 2 [|101.;201.;102.;202.|])
largeM.[98..,98..] |> should equal (DenseMatrix.raw 2 2 [|9898.;9998.;9899.;9999.|])
largeM.[..1,..1] |> should equal (DenseMatrix.raw 2 2 [|0.;100.;1.;101.|])
[<Test>]
let ``Matrix.SetSlice`` () =
let m = DenseMatrix.init 2 2 (fun i j -> float i * 100.0 + float j) in
m.[*,*] <- DenseMatrix(2,2,[|5.;6.;7.;8.|]);
m |> should equal (DenseMatrix(2,2,[|5.;6.;7.;8.|]))
m.[*,*] <- matrix [[5.;7.];[6.;8.]];
m |> should equal (DenseMatrix.raw 2 2 [|5.;6.;7.;8.|])
let m = DenseMatrix.init 2 2 (fun i j -> float i * 100.0 + float j) in
m.[0..1,0..1] <- DenseMatrix(2,2,[|5.;6.;7.;8.|]);
m |> should equal (DenseMatrix(2,2,[|5.;6.;7.;8.|]))
m.[0..1,0..1] <-matrix [[5.;7.];[6.;8.]];
m |> should equal (DenseMatrix.raw 2 2 [|5.;6.;7.;8.|])
let m = DenseMatrix.init 4 4 (fun i j -> float i * 100.0 + float j) in
m.[1..2,1..2] <- DenseMatrix(2,2,[|5.;6.;7.;8.|]);
m |> should equal (DenseMatrix(4,4,[|0.;100.;200.;300.;1.;5.;6.;301.;2.;7.;8.;302.;3.;103.;203.;303.|]))
m.[1..2,1..2] <- matrix [[5.;7.];[6.;8.]];
m |> should equal (DenseMatrix.raw 4 4 [|0.;100.;200.;300.;1.;5.;6.;301.;2.;7.;8.;302.;3.;103.;203.;303.|])
let m = DenseMatrix.init 4 4 (fun i j -> float i * 100.0 + float j) in
m.[2..,..1] <- DenseMatrix(2,2,[|5.;6.;7.;8.|]);
m |> should equal (DenseMatrix(4,4,[|0.;100.;5.;6.;1.;101.;7.;8.;2.;102.;202.;302.;3.;103.;203.;303.|]))
m.[2..,..1] <- matrix [[5.;7.];[6.;8.]];
m |> should equal (DenseMatrix.raw 4 4 [|0.;100.;5.;6.;1.;101.;7.;8.;2.;102.;202.;302.;3.;103.;203.;303.|])
let m = DenseMatrix.init 4 4 (fun i j -> float i * 100.0 + float j) in
m.[..1,2..] <- DenseMatrix(2,2,[|5.;6.;7.;8.|]);
m |> should equal (DenseMatrix(4,4,[|0.;100.;200.;300.;1.;101.;201.;301.;5.;6.;202.;302.;7.;8.;203.;303.|]))
m.[..1,2..] <- matrix [[5.;7.];[6.;8.]];
m |> should equal (DenseMatrix.raw 4 4 [|0.;100.;200.;300.;1.;101.;201.;301.;5.;6.;202.;302.;7.;8.;203.;303.|])
[<Test>]
let ``Matrix.toArray2`` () =

5
src/FSharpUnitTests/SparseMatrixTests.fs

@ -3,7 +3,6 @@
open NUnit.Framework
open FsUnit
open MathNet.Numerics.LinearAlgebra
open MathNet.Numerics.LinearAlgebra.Double
/// Unit tests for the sparse matrix type.
module SparseMatrixTests =
@ -50,11 +49,11 @@ module SparseMatrixTests =
[<Test>]
let ``SparseMatrix.constDiag`` () =
SparseMatrix.createDiag 100 100 2.0 |> should equal (2.0 * (SparseMatrix.Identity 100))
SparseMatrix.createDiag 100 100 2.0 |> should equal (2.0 * (SparseMatrix.identity 100 100))
[<Test>]
let ``SparseMatrix.ofDiag`` () =
SparseMatrix.ofDiag (DenseVector.Create(100, fun i -> 2.0)) |> should equal (2.0 * (SparseMatrix.Identity 100))
SparseMatrix.ofDiag (DenseVector.init 100 (fun i -> 2.0)) |> should equal (2.0 * (SparseMatrix.identity 100 100))
[<Test>]
let ``SparseMatrix.init_row`` () =

4
src/FSharpUnitTests/SparseVectorTests.fs

@ -3,17 +3,15 @@
open NUnit.Framework
open FsUnit
open MathNet.Numerics.LinearAlgebra
open MathNet.Numerics.LinearAlgebra.Double
/// Unit tests for the sparse vector type.
module SparseVectorTests =
/// A small uniform vector.
let smallv = new DenseVector( [|0.0;0.3;0.0;0.0;0.0|] ) :> Vector<float>
let smallv = DenseVector.raw [|0.0;0.3;0.0;0.0;0.0|]
[<Test>]
let ``SparseVector.ofListi`` () = SparseVector.ofListi 5 [ (1,0.3) ] |> should equal smallv
[<Test>]
let ``SparseVector.ofSeqi`` () = SparseVector.ofSeqi 5 (List.toSeq [ (1,0.3) ]) |> should equal smallv

29
src/FSharpUnitTests/VectorTests.fs

@ -3,7 +3,6 @@
open NUnit.Framework
open FsUnit
open MathNet.Numerics.LinearAlgebra
open MathNet.Numerics.LinearAlgebra.Double
/// Unit tests for the vector type.
module VectorTests =
@ -23,27 +22,27 @@ module VectorTests =
let ``Vector.GetSlice`` () =
largev.[*] |> should equal largev
largev.[0..99] |> should equal largev
largev.[1..3] |> should equal (DenseVector([|0.01;0.02;0.03|]))
largev.[97..] |> should equal (DenseVector([|0.97;0.98;0.99|]))
largev.[..4] |> should equal (DenseVector([|0.00;0.01;0.02;0.03;0.04|]))
largev.[1..3] |> should equal (DenseVector.raw [|0.01;0.02;0.03|])
largev.[97..] |> should equal (DenseVector.raw [|0.97;0.98;0.99|])
largev.[..4] |> should equal (DenseVector.raw [|0.00;0.01;0.02;0.03;0.04|])
[<Test>]
let ``Vector.SetSlice`` () =
let v = smallv.Clone() in
v.[*] <- DenseVector([|0.1;0.2;0.3;0.4;0.5|]);
v |> should equal (DenseVector([|0.1;0.2;0.3;0.4;0.5|]))
v.[*] <- vector [0.1;0.2;0.3;0.4;0.5];
v |> should equal (DenseVector.raw [|0.1;0.2;0.3;0.4;0.5|])
let v = smallv.Clone() in
v.[0..4] <- DenseVector([|0.1;0.2;0.3;0.4;0.5|]);
v |> should equal (DenseVector([|0.1;0.2;0.3;0.4;0.5|]))
v.[0..4] <- vector [0.1;0.2;0.3;0.4;0.5];
v |> should equal (DenseVector.raw [|0.1;0.2;0.3;0.4;0.5|])
let v = smallv.Clone() in
v.[1..3] <- DenseVector([|7.0;8.0;9.0|]);
v |> should equal (DenseVector([|0.3;7.0;8.0;9.0;0.3|]))
v.[1..3] <- vector [7.0;8.0;9.0];
v |> should equal (DenseVector.raw [|0.3;7.0;8.0;9.0;0.3|])
let v = smallv.Clone() in
v.[2..] <- DenseVector([|7.0;8.0;9.0|]);
v |> should equal (DenseVector([|0.3;0.3;7.0;8.0;9.0|]))
v.[2..] <- vector [7.0;8.0;9.0];
v |> should equal (DenseVector.raw [|0.3;0.3;7.0;8.0;9.0|])
let v = smallv.Clone() in
v.[..2] <- DenseVector([|7.0;8.0;9.0|]);
v |> should equal (DenseVector([|7.0;8.0;9.0;0.3;0.3|]))
v.[..2] <- vector [7.0;8.0;9.0];
v |> should equal (DenseVector.raw [|7.0;8.0;9.0;0.3;0.3|])
[<Test>]
let ``Vector.toArray`` () =
@ -163,7 +162,7 @@ module VectorTests =
[<Test>]
let ``Vector.insert`` () =
Vector.insert 2 0.5 smallv |> should (approximately_equal 14) (new DenseVector ( [|0.3;0.3;0.5;0.3;0.3;0.3|] ) :> Vector<float>)
Vector.insert 2 0.5 smallv |> should (approximately_equal 14) (DenseVector.raw [|0.3;0.3;0.5;0.3;0.3;0.3|])
[<Test>]
let ``Pointwise Multiplication using .* Operator`` () =

2
src/Numerics/LinearAlgebra/Builder.cs

@ -940,7 +940,7 @@ namespace MathNet.Numerics.LinearAlgebra
/// This new vector will be independent from the enumerable.
/// A new memory block will be allocated for storing the vector.
/// </summary>
public Vector<T> DenseVectorOfIndexedEnumerable(int length, IEnumerable<Tuple<int, T>> enumerable)
public Vector<T> DenseVectorOfIndexed(int length, IEnumerable<Tuple<int, T>> enumerable)
{
return DenseVector(DenseVectorStorage<T>.OfIndexedEnumerable(length, enumerable));
}

Loading…
Cancel
Save