Use C# 8.0 and enable nullable reference types #10
@ -1,6 +1,6 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
<PropertyGroup>
|
||||
<TargetFramework>netcoreapp2.0</TargetFramework>
|
||||
<TargetFramework>netcoreapp3.0</TargetFramework>
|
||||
<IsPackable>false</IsPackable>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'">
|
||||
|
@ -33,8 +33,8 @@ namespace MatFileHandler
|
||||
DataElement data,
|
||||
DataElement imaginaryData)
|
||||
{
|
||||
var realParts = DataExtraction.GetDataAsDouble(data).ToArrayLazily();
|
||||
var imaginaryParts = DataExtraction.GetDataAsDouble(imaginaryData).ToArrayLazily();
|
||||
var realParts = DataExtraction.GetDataAsDouble(data);
|
||||
var imaginaryParts = DataExtraction.GetDataAsDouble(imaginaryData);
|
||||
if (realParts == null)
|
||||
{
|
||||
throw new HandlerException("Couldn't read sparse array.");
|
||||
@ -106,12 +106,12 @@ namespace MatFileHandler
|
||||
int[] dimensions,
|
||||
string name,
|
||||
DataElement realData,
|
||||
DataElement imaginaryData)
|
||||
DataElement? imaginaryData)
|
||||
where T : struct
|
||||
{
|
||||
if (flags.Variable.HasFlag(Variable.IsLogical))
|
||||
{
|
||||
var data = DataExtraction.GetDataAsUInt8(realData).ToArrayLazily().Select(x => x != 0).ToArray();
|
||||
var data = DataExtraction.GetDataAsUInt8(realData).Select(x => x != 0).ToArray();
|
||||
return new MatNumericalArrayOf<bool>(flags, dimensions, name, data);
|
||||
}
|
||||
switch (flags.Class)
|
||||
@ -139,6 +139,11 @@ namespace MatFileHandler
|
||||
var dataArray = ConvertDataToProperType<T>(realData, flags.Class);
|
||||
if (flags.Variable.HasFlag(Variable.IsComplex))
|
||||
{
|
||||
if (imaginaryData is null)
|
||||
{
|
||||
throw new HandlerException("Imaginary part of a complex variable not found.");
|
||||
}
|
||||
|
||||
var dataArray2 = ConvertDataToProperType<T>(imaginaryData, flags.Class);
|
||||
if (flags.Class == ArrayType.MxDouble)
|
||||
{
|
||||
@ -163,49 +168,26 @@ namespace MatFileHandler
|
||||
string name,
|
||||
MiNum<byte> dataElement)
|
||||
{
|
||||
var data = dataElement?.Data;
|
||||
var data = dataElement.Data;
|
||||
return new MatCharArrayOf<byte>(flags, dimensions, name, data, Encoding.UTF8.GetString(data));
|
||||
}
|
||||
|
||||
private static T[] ConvertDataToProperType<T>(DataElement data, ArrayType arrayType)
|
||||
{
|
||||
switch (arrayType)
|
||||
{
|
||||
case ArrayType.MxDouble:
|
||||
return DataExtraction.GetDataAsDouble(data).ToArrayLazily() as T[];
|
||||
case ArrayType.MxSingle:
|
||||
return DataExtraction.GetDataAsSingle(data).ToArrayLazily() as T[];
|
||||
case ArrayType.MxInt8:
|
||||
return DataExtraction.GetDataAsInt8(data).ToArrayLazily() as T[];
|
||||
case ArrayType.MxUInt8:
|
||||
return DataExtraction.GetDataAsUInt8(data).ToArrayLazily() as T[];
|
||||
case ArrayType.MxInt16:
|
||||
return DataExtraction.GetDataAsInt16(data).ToArrayLazily() as T[];
|
||||
case ArrayType.MxUInt16:
|
||||
return DataExtraction.GetDataAsUInt16(data).ToArrayLazily() as T[];
|
||||
case ArrayType.MxInt32:
|
||||
return DataExtraction.GetDataAsInt32(data).ToArrayLazily() as T[];
|
||||
case ArrayType.MxUInt32:
|
||||
return DataExtraction.GetDataAsUInt32(data).ToArrayLazily() as T[];
|
||||
case ArrayType.MxInt64:
|
||||
return DataExtraction.GetDataAsInt64(data).ToArrayLazily() as T[];
|
||||
case ArrayType.MxUInt64:
|
||||
return DataExtraction.GetDataAsUInt64(data).ToArrayLazily() as T[];
|
||||
default:
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
return TryConvertDataToProperType<T>(data, arrayType)
|
||||
?? throw new HandlerException($"Unexpected data type.");
|
||||
}
|
||||
|
||||
private static T[] ConvertDataToSparseProperType<T>(DataElement data, bool isLogical)
|
||||
private static T[]? ConvertDataToSparseProperType<T>(DataElement data, bool isLogical)
|
||||
{
|
||||
if (isLogical)
|
||||
{
|
||||
return DataExtraction.GetDataAsUInt8(data).ToArrayLazily().Select(x => x != 0).ToArray() as T[];
|
||||
return DataExtraction.GetDataAsUInt8(data).Select(x => x != 0).ToArray() as T[];
|
||||
}
|
||||
switch (data)
|
||||
{
|
||||
case MiNum<double> _:
|
||||
return DataExtraction.GetDataAsDouble(data).ToArrayLazily() as T[];
|
||||
return DataExtraction.GetDataAsDouble(data) as T[];
|
||||
default:
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
@ -217,7 +199,7 @@ namespace MatFileHandler
|
||||
string name,
|
||||
MiNum<ushort> dataElement)
|
||||
{
|
||||
var data = dataElement?.Data;
|
||||
var data = dataElement.Data;
|
||||
return new MatCharArrayOf<ushort>(
|
||||
flags,
|
||||
dimensions,
|
||||
@ -226,7 +208,7 @@ namespace MatFileHandler
|
||||
new string(data.Select(x => (char)x).ToArray()));
|
||||
}
|
||||
|
||||
private static Dictionary<(int, int), T> ConvertMatlabSparseToDictionary<T>(
|
||||
private static Dictionary<(int row, int column), T> ConvertMatlabSparseToDictionary<T>(
|
||||
int[] rowIndex,
|
||||
int[] columnIndex,
|
||||
Func<int, T> get)
|
||||
@ -242,5 +224,23 @@ namespace MatFileHandler
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
private static T[]? TryConvertDataToProperType<T>(DataElement data, ArrayType arrayType)
|
||||
{
|
||||
return arrayType switch
|
||||
{
|
||||
ArrayType.MxDouble => DataExtraction.GetDataAsDouble(data) as T[],
|
||||
ArrayType.MxSingle => DataExtraction.GetDataAsSingle(data) as T[],
|
||||
ArrayType.MxInt8 => DataExtraction.GetDataAsInt8(data) as T[],
|
||||
ArrayType.MxUInt8 => DataExtraction.GetDataAsUInt8(data) as T[],
|
||||
ArrayType.MxInt16 => DataExtraction.GetDataAsInt16(data) as T[],
|
||||
ArrayType.MxUInt16 => DataExtraction.GetDataAsUInt16(data) as T[],
|
||||
ArrayType.MxInt32 => DataExtraction.GetDataAsInt32(data) as T[],
|
||||
ArrayType.MxUInt32 => DataExtraction.GetDataAsUInt32(data) as T[],
|
||||
ArrayType.MxInt64 => DataExtraction.GetDataAsInt64(data) as T[],
|
||||
ArrayType.MxUInt64 => DataExtraction.GetDataAsUInt64(data) as T[],
|
||||
_ => throw new NotSupportedException()
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
@ -194,7 +194,7 @@ namespace MatFileHandler
|
||||
};
|
||||
}
|
||||
|
||||
private static (BinaryReader, Tag) ReadTag(BinaryReader reader)
|
||||
private static (BinaryReader reader, Tag tag) ReadTag(BinaryReader reader)
|
||||
{
|
||||
var type = reader.ReadInt32();
|
||||
var typeHi = type >> 16;
|
||||
@ -222,7 +222,8 @@ namespace MatFileHandler
|
||||
var elements = new List<IArray>();
|
||||
for (var i = 0; i < numberOfElements; i++)
|
||||
{
|
||||
var element = Read(reader) as IArray;
|
||||
var element = Read(reader) as IArray
|
||||
?? throw new HandlerException("Unable to read cell array.");
|
||||
elements.Add(element);
|
||||
}
|
||||
|
||||
@ -319,8 +320,9 @@ namespace MatFileHandler
|
||||
string name,
|
||||
int fieldNameLength)
|
||||
{
|
||||
var element = Read(reader);
|
||||
var fieldNames = ReadFieldNames(element as MiNum<sbyte>, fieldNameLength);
|
||||
var element = Read(reader) as MiNum<sbyte>
|
||||
?? throw new HandlerException("Unable to parse structure field names.");
|
||||
var fieldNames = ReadFieldNames(element, fieldNameLength);
|
||||
var fields = new Dictionary<string, List<IArray>>();
|
||||
foreach (var fieldName in fieldNames)
|
||||
{
|
||||
@ -332,7 +334,8 @@ namespace MatFileHandler
|
||||
{
|
||||
foreach (var fieldName in fieldNames)
|
||||
{
|
||||
var field = Read(reader) as IArray;
|
||||
var field = Read(reader) as IArray
|
||||
?? throw new HandlerException("Unable to parse field name.");
|
||||
fields[fieldName].Add(field);
|
||||
}
|
||||
}
|
||||
@ -398,7 +401,7 @@ namespace MatFileHandler
|
||||
|
||||
var element4 = Read(reader);
|
||||
var data = ReadData(element4);
|
||||
DataElement imaginaryData = null;
|
||||
DataElement? imaginaryData = null;
|
||||
if (flags.Variable.HasFlag(Variable.IsComplex))
|
||||
{
|
||||
var element5 = Read(reader);
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -30,20 +30,24 @@ namespace MatFileHandler
|
||||
}
|
||||
|
||||
epoch = new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc);
|
||||
var dataArray = matObject["data", 0] as IArrayOf<double>;
|
||||
if (dataArray is null)
|
||||
|
||||
switch (matObject["data", 0])
|
||||
{
|
||||
var dataComplex = matObject["data", 0] as IArrayOf<Complex>;
|
||||
var complexData = dataComplex.ConvertToComplexArray();
|
||||
case IArrayOf<double> dataArray:
|
||||
data = dataArray.ConvertToDoubleArray()
|
||||
?? throw new HandlerException("Cannot extract data for the datetime adapter.");
|
||||
data2 = new double[data.Length];
|
||||
dimensions = dataArray.Dimensions;
|
||||
break;
|
||||
case IArrayOf<Complex> dataComplex:
|
||||
var complexData = dataComplex.ConvertToComplexArray()
|
||||
?? throw new HandlerException("Cannot extract data for the datetime adapter.");
|
||||
data = complexData.Select(c => c.Real).ToArray();
|
||||
data2 = complexData.Select(c => c.Imaginary).ToArray();
|
||||
dimensions = dataComplex.Dimensions;
|
||||
}
|
||||
else
|
||||
{
|
||||
data = dataArray.ConvertToDoubleArray();
|
||||
data2 = new double[data.Length];
|
||||
dimensions = dataArray.Dimensions;
|
||||
break;
|
||||
default:
|
||||
throw new HandlerException("Datetime data not found.");
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -25,7 +25,8 @@ namespace MatFileHandler
|
||||
}
|
||||
|
||||
var dataObject = matObject["millis", 0];
|
||||
data = dataObject.ConvertToDoubleArray();
|
||||
data = dataObject.ConvertToDoubleArray()
|
||||
?? throw new HandlerException("Cannot extract data for the duration adapter.");
|
||||
dimensions = dataObject.Dimensions;
|
||||
}
|
||||
|
||||
|
@ -5,7 +5,7 @@ using System;
|
||||
namespace MatFileHandler
|
||||
{
|
||||
/// <summary>
|
||||
/// Exception related to Matlab data handling
|
||||
/// Exception related to Matlab data handling.
|
||||
/// </summary>
|
||||
public class HandlerException : Exception
|
||||
{
|
||||
@ -14,7 +14,7 @@ namespace MatFileHandler
|
||||
/// </summary>
|
||||
/// <param name="message">Error message.</param>
|
||||
/// <param name="innerException">Inner exception.</param>
|
||||
public HandlerException(string message, Exception innerException = null)
|
||||
public HandlerException(string message, Exception? innerException = null)
|
||||
: base(message, innerException)
|
||||
{
|
||||
}
|
||||
|
@ -28,12 +28,12 @@ namespace MatFileHandler
|
||||
/// Tries to convert the array to an array of Double values.
|
||||
/// </summary>
|
||||
/// <returns>Array of values of the array, converted to Double, or null if the conversion is not possible.</returns>
|
||||
double[] ConvertToDoubleArray();
|
||||
double[]? ConvertToDoubleArray();
|
||||
|
||||
/// <summary>
|
||||
/// Tries to convert the array to an array of Complex values.
|
||||
/// </summary>
|
||||
/// <returns>Array of values of the array, converted to Complex, or null if the conversion is not possible.</returns>
|
||||
Complex[] ConvertToComplexArray();
|
||||
Complex[]? ConvertToComplexArray();
|
||||
}
|
||||
}
|
@ -21,7 +21,7 @@ namespace MatFileHandler
|
||||
/// * for cell arrays:
|
||||
/// IArray;
|
||||
/// * for structure arrays:
|
||||
/// IReadOnlyDictionary<string, IArray>;
|
||||
/// IReadOnlyDictionary<string, IArray>.
|
||||
/// </remarks>
|
||||
public interface IArrayOf<T> : IArray
|
||||
{
|
||||
|
@ -15,6 +15,6 @@ namespace MatFileHandler
|
||||
/// <summary>
|
||||
/// Gets a dictionary mapping indices to values.
|
||||
/// </summary>
|
||||
new IReadOnlyDictionary<(int, int), T> Data { get; }
|
||||
new IReadOnlyDictionary<(int row, int column), T> Data { get; }
|
||||
}
|
||||
}
|
@ -54,13 +54,13 @@ namespace MatFileHandler
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public virtual double[] ConvertToDoubleArray()
|
||||
public virtual double[]? ConvertToDoubleArray()
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public virtual Complex[] ConvertToComplexArray()
|
||||
public virtual Complex[]? ConvertToComplexArray()
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
@ -15,6 +15,8 @@
|
||||
<OutputPath>bin\$(Configuration)\</OutputPath>
|
||||
<DocumentationFile>$(OutputPath)\$(TargetFramework)\$(AssemblyName).xml</DocumentationFile>
|
||||
<GeneratePackageOnBuild>true</GeneratePackageOnBuild>
|
||||
<LangVersion>8.0</LangVersion>
|
||||
<Nullable>enable</Nullable>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'">
|
||||
<CodeAnalysisRuleSet>..\MatFileHandler.ruleset</CodeAnalysisRuleSet>
|
||||
@ -26,7 +28,7 @@
|
||||
<AdditionalFiles Include="..\stylecop.json" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<PackageReference Include="StyleCop.Analyzers" Version="1.1.0-beta004">
|
||||
<PackageReference Include="StyleCop.Analyzers" Version="1.2.0-beta.66">
|
||||
<PrivateAssets>All</PrivateAssets>
|
||||
</PackageReference>
|
||||
<PackageReference Include="System.ValueTuple" Version="4.4.0" Condition="'$(TargetFramework)' == 'net461'" />
|
||||
|
@ -57,7 +57,8 @@ namespace MatFileHandler
|
||||
var dataElement = dataElementReader.Read(reader);
|
||||
if (position == subsystemDataOffset)
|
||||
{
|
||||
var subsystemDataElement = dataElement as IArrayOf<byte>;
|
||||
var subsystemDataElement = dataElement as IArrayOf<byte>
|
||||
?? throw new HandlerException("Cannot parse subsystem data element.");
|
||||
var newSubsystemData = ReadSubsystemData(subsystemDataElement.Data, subsystemData);
|
||||
subsystemData.Set(newSubsystemData);
|
||||
}
|
||||
|
@ -198,14 +198,14 @@ namespace MatFileHandler
|
||||
return buffer;
|
||||
}
|
||||
|
||||
private (byte[], byte[]) ConvertToPairOfByteArrays<T>(ComplexOf<T>[] data)
|
||||
private (byte[] real, byte[] imaginary) ConvertToPairOfByteArrays<T>(ComplexOf<T>[] data)
|
||||
where T : struct
|
||||
{
|
||||
return (ConvertToByteArray(data.Select(x => x.Real).ToArray()),
|
||||
ConvertToByteArray(data.Select(x => x.Imaginary).ToArray()));
|
||||
}
|
||||
|
||||
private (byte[], byte[]) ConvertToPairOfByteArrays(Complex[] data)
|
||||
private (byte[] real, byte[] imaginary) ConvertToPairOfByteArrays(Complex[] data)
|
||||
{
|
||||
return (ConvertToByteArray(data.Select(x => x.Real).ToArray()),
|
||||
ConvertToByteArray(data.Select(x => x.Imaginary).ToArray()));
|
||||
@ -496,8 +496,8 @@ namespace MatFileHandler
|
||||
for (var column = 0; column < numberOfColumns; column++)
|
||||
{
|
||||
var column1 = column;
|
||||
var thisColumn = keys.Where(pair => pair.Item2 == column1 && !dict[pair].Equals(default(T)));
|
||||
var thisRow = thisColumn.Select(pair => pair.Item1).OrderBy(x => x).ToArray();
|
||||
var thisColumn = keys.Where(pair => pair.column == column1 && !dict[pair].Equals(default));
|
||||
var thisRow = thisColumn.Select(pair => pair.row).OrderBy(x => x).ToArray();
|
||||
rowIndexList.AddRange(thisRow);
|
||||
valuesList.AddRange(thisRow.Select(row => dict[(row, column1)]));
|
||||
columnIndex[column + 1] = rowIndexList.Count;
|
||||
|
@ -43,58 +43,152 @@ namespace MatFileHandler
|
||||
/// <returns>Array of values of the array, converted to Double, or null if the conversion is not possible.</returns>
|
||||
public override double[] ConvertToDoubleArray()
|
||||
{
|
||||
return Data as double[] ?? Data.Select(x => Convert.ToDouble(x)).ToArray();
|
||||
return Data switch
|
||||
{
|
||||
sbyte[] sbyteData => DataExtraction.SbyteToDouble(sbyteData),
|
||||
byte[] byteData => DataExtraction.ByteToDouble(byteData),
|
||||
short[] shortData => DataExtraction.ShortToDouble(shortData),
|
||||
ushort[] ushortData => DataExtraction.UshortToDouble(ushortData),
|
||||
int[] intData => DataExtraction.IntToDouble(intData),
|
||||
uint[] uintData => DataExtraction.UintToDouble(uintData),
|
||||
long[] longData => DataExtraction.LongToDouble(longData),
|
||||
ulong[] ulongData => DataExtraction.UlongToDouble(ulongData),
|
||||
float[] floatData => DataExtraction.FloatToDouble(floatData),
|
||||
double[] doubleData => doubleData,
|
||||
_ => throw new HandlerException("Cannot convert data to double array.")
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Tries to convert the array to an array of Complex values.
|
||||
/// </summary>
|
||||
/// <returns>Array of values of the array, converted to Complex, or null if the conversion is not possible.</returns>
|
||||
public override Complex[] ConvertToComplexArray()
|
||||
public override Complex[]? ConvertToComplexArray()
|
||||
{
|
||||
if (Data is Complex[])
|
||||
return Data switch
|
||||
{
|
||||
return Data as Complex[];
|
||||
}
|
||||
if (Data is ComplexOf<sbyte>[])
|
||||
{
|
||||
return ConvertToComplex(Data as ComplexOf<sbyte>[]);
|
||||
}
|
||||
if (Data is ComplexOf<byte>[])
|
||||
{
|
||||
return ConvertToComplex(Data as ComplexOf<byte>[]);
|
||||
}
|
||||
if (Data is ComplexOf<short>[])
|
||||
{
|
||||
return ConvertToComplex(Data as ComplexOf<short>[]);
|
||||
}
|
||||
if (Data is ComplexOf<ushort>[])
|
||||
{
|
||||
return ConvertToComplex(Data as ComplexOf<ushort>[]);
|
||||
}
|
||||
if (Data is ComplexOf<int>[])
|
||||
{
|
||||
return ConvertToComplex(Data as ComplexOf<int>[]);
|
||||
}
|
||||
if (Data is ComplexOf<uint>[])
|
||||
{
|
||||
return ConvertToComplex(Data as ComplexOf<uint>[]);
|
||||
}
|
||||
if (Data is ComplexOf<long>[])
|
||||
{
|
||||
return ConvertToComplex(Data as ComplexOf<long>[]);
|
||||
}
|
||||
if (Data is ComplexOf<ulong>[])
|
||||
{
|
||||
return ConvertToComplex(Data as ComplexOf<ulong>[]);
|
||||
}
|
||||
return ConvertToDoubleArray().Select(x => new Complex(x, 0.0)).ToArray();
|
||||
Complex[] data => data,
|
||||
ComplexOf<sbyte>[] ofs => ConvertToComplex(ofs),
|
||||
ComplexOf<byte>[] ofs => ConvertToComplex(ofs),
|
||||
ComplexOf<short>[] ofs => ConvertToComplex(ofs),
|
||||
ComplexOf<ushort>[] ofs => ConvertToComplex(ofs),
|
||||
ComplexOf<int>[] ofs => ConvertToComplex(ofs),
|
||||
ComplexOf<uint>[] ofs => ConvertToComplex(ofs),
|
||||
ComplexOf<long>[] ofs => ConvertToComplex(ofs),
|
||||
ComplexOf<ulong>[] ofs => ConvertToComplex(ofs),
|
||||
ComplexOf<float>[] ofs => ConvertToComplex(ofs),
|
||||
_ => ConvertToComplex(ConvertToDoubleArray())
|
||||
};
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex<TS>(IEnumerable<ComplexOf<TS>> array)
|
||||
where TS : struct
|
||||
private static Complex[] ConvertToComplex(ComplexOf<sbyte>[] array)
|
||||
{
|
||||
return array.Select(x => new Complex(Convert.ToDouble(x.Real), Convert.ToDouble(x.Imaginary))).ToArray();
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(Convert.ToDouble(array[i].Real), Convert.ToDouble(array[i].Imaginary));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex(ComplexOf<byte>[] array)
|
||||
{
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(Convert.ToDouble(array[i].Real), Convert.ToDouble(array[i].Imaginary));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex(ComplexOf<short>[] array)
|
||||
{
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(Convert.ToDouble(array[i].Real), Convert.ToDouble(array[i].Imaginary));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex(ComplexOf<ushort>[] array)
|
||||
{
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(Convert.ToDouble(array[i].Real), Convert.ToDouble(array[i].Imaginary));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex(ComplexOf<int>[] array)
|
||||
{
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(Convert.ToDouble(array[i].Real), Convert.ToDouble(array[i].Imaginary));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex(ComplexOf<uint>[] array)
|
||||
{
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(Convert.ToDouble(array[i].Real), Convert.ToDouble(array[i].Imaginary));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex(ComplexOf<long>[] array)
|
||||
{
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(Convert.ToDouble(array[i].Real), Convert.ToDouble(array[i].Imaginary));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex(ComplexOf<ulong>[] array)
|
||||
{
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(Convert.ToDouble(array[i].Real), Convert.ToDouble(array[i].Imaginary));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex(ComplexOf<float>[] array)
|
||||
{
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(Convert.ToDouble(array[i].Real), Convert.ToDouble(array[i].Imaginary));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static Complex[] ConvertToComplex(double[] array)
|
||||
{
|
||||
var result = new Complex[array.Length];
|
||||
for (var i = 0; i < array.Length; i++)
|
||||
{
|
||||
result[i] = new Complex(array[i], 0.0);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
@ -26,7 +26,7 @@ namespace MatFileHandler
|
||||
SparseArrayFlags flags,
|
||||
int[] dimensions,
|
||||
string name,
|
||||
Dictionary<(int, int), T> data)
|
||||
Dictionary<(int row, int column), T> data)
|
||||
: base(flags.ArrayFlags, dimensions, name)
|
||||
{
|
||||
DataDictionary = data;
|
||||
@ -39,9 +39,9 @@ namespace MatFileHandler
|
||||
.ToArray();
|
||||
|
||||
/// <inheritdoc />
|
||||
public IReadOnlyDictionary<(int, int), T> Data => DataDictionary;
|
||||
public IReadOnlyDictionary<(int row, int column), T> Data => DataDictionary;
|
||||
|
||||
private Dictionary<(int, int), T> DataDictionary { get; }
|
||||
private Dictionary<(int row, int column), T> DataDictionary { get; }
|
||||
|
||||
/// <inheritdoc />
|
||||
public T this[params int[] list]
|
||||
|
@ -35,7 +35,19 @@ namespace MatFileHandler
|
||||
/// <summary>
|
||||
/// Gets null: not implemented.
|
||||
/// </summary>
|
||||
public IReadOnlyDictionary<string, IArray>[] Data => null;
|
||||
public IReadOnlyDictionary<string, IArray>[] Data
|
||||
{
|
||||
get
|
||||
{
|
||||
var result = new IReadOnlyDictionary<string, IArray>[Count];
|
||||
for (var i = 0; i < Count; i++)
|
||||
{
|
||||
result[i] = FieldNames.ToDictionary(name => name, name => Fields[name][i]);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a dictionary that maps field names to lists of values.
|
||||
@ -128,7 +140,7 @@ namespace MatFileHandler
|
||||
/// <summary>
|
||||
/// Checks if the structure has a given field.
|
||||
/// </summary>
|
||||
/// <param name="key">Field name</param>
|
||||
/// <param name="key">Field name.</param>
|
||||
/// <returns>True iff the structure has a given field.</returns>
|
||||
public bool ContainsKey(string key) => Parent.Fields.ContainsKey(key);
|
||||
|
||||
@ -138,12 +150,14 @@ namespace MatFileHandler
|
||||
/// <param name="key">Field name.</param>
|
||||
/// <param name="value">Value (or null if the field is not present).</param>
|
||||
/// <returns>Success status of the query.</returns>
|
||||
public bool TryGetValue(string key, out IArray value)
|
||||
#pragma warning disable CS8614
|
||||
public bool TryGetValue(string key, out IArray? value)
|
||||
#pragma warning restore CS8614
|
||||
{
|
||||
var success = Parent.Fields.TryGetValue(key, out var array);
|
||||
if (!success)
|
||||
{
|
||||
value = default(IArray);
|
||||
value = default;
|
||||
return false;
|
||||
}
|
||||
value = array[Index];
|
||||
|
@ -50,9 +50,9 @@ namespace MatFileHandler
|
||||
public string TypeDescription { get; }
|
||||
|
||||
/// <inheritdoc />
|
||||
public override Complex[] ConvertToComplexArray() => null;
|
||||
public override Complex[]? ConvertToComplexArray() => null;
|
||||
|
||||
/// <inheritdoc />
|
||||
public override double[] ConvertToDoubleArray() => null;
|
||||
public override double[]? ConvertToDoubleArray() => null;
|
||||
}
|
||||
}
|
@ -47,7 +47,21 @@ namespace MatFileHandler
|
||||
public int ClassIndex { get; }
|
||||
|
||||
/// <inheritdoc />
|
||||
public IReadOnlyDictionary<string, IArray>[] Data => null;
|
||||
public IReadOnlyDictionary<string, IArray>[] Data
|
||||
{
|
||||
get
|
||||
{
|
||||
var result = new IReadOnlyDictionary<string, IArray>[Count];
|
||||
for (var i = 0; i < Count; i++)
|
||||
{
|
||||
result[i] = FieldNamesArray.ToDictionary(
|
||||
name => name,
|
||||
name => this[name, i]);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public IEnumerable<string> FieldNames => FieldNamesArray;
|
||||
@ -71,7 +85,7 @@ namespace MatFileHandler
|
||||
{
|
||||
if (TryGetValue(field, out var result, list))
|
||||
{
|
||||
return result;
|
||||
return result!;
|
||||
}
|
||||
|
||||
throw new IndexOutOfRangeException();
|
||||
@ -91,19 +105,19 @@ namespace MatFileHandler
|
||||
return new OpaqueObjectArrayElement(this, i);
|
||||
}
|
||||
|
||||
private bool TryGetValue(string field, out IArray output, params int[] list)
|
||||
private bool TryGetValue(string field, out IArray? output, params int[] list)
|
||||
{
|
||||
var index = Dimensions.DimFlatten(list);
|
||||
var maybeFieldIndex = subsystemData.ClassInformation[ClassIndex].FindField(field);
|
||||
if (!(maybeFieldIndex is int fieldIndex))
|
||||
{
|
||||
output = default(IArray);
|
||||
output = default;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (index >= IndexToObjectId.Length)
|
||||
{
|
||||
output = default(IArray);
|
||||
output = default;
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -161,7 +175,9 @@ namespace MatFileHandler
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public bool TryGetValue(string key, out IArray value)
|
||||
#pragma warning disable CS8614
|
||||
public bool TryGetValue(string key, out IArray? value)
|
||||
#pragma warning restore CS8614
|
||||
{
|
||||
return parent.TryGetValue(key, out value, index);
|
||||
}
|
||||
|
@ -25,7 +25,8 @@ namespace MatFileHandler
|
||||
throw new ArgumentException("The object provided is not a string.");
|
||||
}
|
||||
|
||||
var binaryData = matObject["any", 0] as IArrayOf<ulong>;
|
||||
var binaryData = matObject["any", 0] as IArrayOf<ulong>
|
||||
?? throw new HandlerException("Cannot extract string data.");
|
||||
|
||||
(dimensions, strings) = ParseBinaryData(binaryData.Data);
|
||||
}
|
||||
|
@ -12,15 +12,15 @@ namespace MatFileHandler
|
||||
/// </summary>
|
||||
internal class SubsystemData
|
||||
{
|
||||
private RealSubsystemData? _realData;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="SubsystemData"/> class.
|
||||
/// Default constructor: initializes everything to null.
|
||||
/// </summary>
|
||||
public SubsystemData()
|
||||
{
|
||||
ClassInformation = null;
|
||||
ObjectInformation = null;
|
||||
Data = null;
|
||||
_realData = null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@ -35,27 +35,29 @@ namespace MatFileHandler
|
||||
Dictionary<int, ObjectInfo> objectInformation,
|
||||
Dictionary<int, IArray> data)
|
||||
{
|
||||
this.ClassInformation =
|
||||
classInformation ?? throw new ArgumentNullException(nameof(classInformation));
|
||||
this.ObjectInformation =
|
||||
objectInformation ?? throw new ArgumentNullException(nameof(objectInformation));
|
||||
this.Data = data ?? throw new ArgumentNullException(nameof(data));
|
||||
_realData = new RealSubsystemData(
|
||||
classInformation,
|
||||
objectInformation,
|
||||
data);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets information about all the classes occurring in the file.
|
||||
/// Gets information about all the classes occurring in the file.
|
||||
/// </summary>
|
||||
public Dictionary<int, ClassInfo> ClassInformation { get; set; }
|
||||
public Dictionary<int, ClassInfo> ClassInformation =>
|
||||
_realData?.ClassInformation ?? throw new HandlerException("Subsystem data missing.");
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the actual data: mapping of "object field" indices to their values.
|
||||
/// Gets the actual data: mapping of "object field" indices to their values.
|
||||
/// </summary>
|
||||
public IReadOnlyDictionary<int, IArray> Data { get; set; }
|
||||
public IReadOnlyDictionary<int, IArray> Data =>
|
||||
_realData?.Data ?? throw new HandlerException("Subsystem data missing.");
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets information about all the objects occurring in the file.
|
||||
/// Gets information about all the objects occurring in the file.
|
||||
/// </summary>
|
||||
public Dictionary<int, ObjectInfo> ObjectInformation { get; set; }
|
||||
public Dictionary<int, ObjectInfo> ObjectInformation =>
|
||||
_realData?.ObjectInformation ?? throw new HandlerException("Subsystem data missing.");
|
||||
|
||||
/// <summary>
|
||||
/// Initialize this object from another object.
|
||||
@ -66,9 +68,10 @@ namespace MatFileHandler
|
||||
/// <param name="data">Another subsystem data.</param>
|
||||
public void Set(SubsystemData data)
|
||||
{
|
||||
this.ClassInformation = data.ClassInformation;
|
||||
this.ObjectInformation = data.ObjectInformation;
|
||||
this.Data = data.Data;
|
||||
_realData = new RealSubsystemData(
|
||||
data.ClassInformation,
|
||||
data.ObjectInformation,
|
||||
data.Data);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@ -136,5 +139,39 @@ namespace MatFileHandler
|
||||
/// </summary>
|
||||
public IReadOnlyDictionary<int, int> FieldLinks => fieldLinks;
|
||||
}
|
||||
|
||||
private class RealSubsystemData
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="RealSubsystemData"/> class.
|
||||
/// </summary>
|
||||
/// <param name="classInformation">Class information.</param>
|
||||
/// <param name="objectInformation">Object information.</param>
|
||||
/// <param name="data">Data.</param>
|
||||
public RealSubsystemData(
|
||||
Dictionary<int, ClassInfo> classInformation,
|
||||
Dictionary<int, ObjectInfo> objectInformation,
|
||||
IReadOnlyDictionary<int, IArray> data)
|
||||
{
|
||||
ClassInformation = classInformation ?? throw new ArgumentNullException(nameof(classInformation));
|
||||
ObjectInformation = objectInformation ?? throw new ArgumentNullException(nameof(objectInformation));
|
||||
Data = data ?? throw new ArgumentNullException(nameof(data));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets information about all the classes occurring in the file.
|
||||
/// </summary>
|
||||
public Dictionary<int, ClassInfo> ClassInformation { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the actual data: mapping of "object field" indices to their values.
|
||||
/// </summary>
|
||||
public IReadOnlyDictionary<int, IArray> Data { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets information about all the objects occurring in the file.
|
||||
/// </summary>
|
||||
public Dictionary<int, ObjectInfo> ObjectInformation { get; }
|
||||
}
|
||||
}
|
||||
}
|
@ -23,65 +23,27 @@ namespace MatFileHandler
|
||||
/// <returns>Subsystem data read.</returns>
|
||||
public static SubsystemData Read(byte[] bytes, SubsystemData subsystemData)
|
||||
{
|
||||
List<RawVariable> rawVariables = null;
|
||||
using (var stream = new MemoryStream(bytes))
|
||||
{
|
||||
using (var reader = new BinaryReader(stream))
|
||||
{
|
||||
reader.ReadBytes(8);
|
||||
rawVariables = MatFileReader.ReadRawVariables(reader, -1, subsystemData);
|
||||
}
|
||||
}
|
||||
var rawVariables = ReadRawVariables(bytes, subsystemData);
|
||||
|
||||
// Parse subsystem data.
|
||||
var mainVariable = rawVariables[0].DataElement as IStructureArray;
|
||||
var mcosData = mainVariable["MCOS", 0] as Opaque;
|
||||
var opaqueData = mcosData.RawData as ICellArray;
|
||||
var info = (opaqueData[0] as IArrayOf<byte>).Data;
|
||||
var mainVariable = rawVariables[0].DataElement as IStructureArray
|
||||
?? throw new HandlerException("Subsystem data must be a structure array.");
|
||||
var mcosData = mainVariable["MCOS", 0] as Opaque
|
||||
?? throw new HandlerException("MCOS data must be an opaque object.");
|
||||
var opaqueData = mcosData.RawData as ICellArray
|
||||
?? throw new HandlerException("Opaque data must be a cell array.");
|
||||
var info = (opaqueData[0] as IArrayOf<byte>)?.Data
|
||||
?? throw new HandlerException("Opaque data info must be a byte array.");
|
||||
var (offsets, position) = ReadOffsets(info, 0);
|
||||
var fieldNames = ReadFieldNames(info, position, offsets[1]);
|
||||
var numberOfClasses = ((offsets[3] - offsets[2]) / 16) - 1;
|
||||
Dictionary<int, string> classIdToName = null;
|
||||
using (var stream = new MemoryStream(info, offsets[2], offsets[3] - offsets[2]))
|
||||
{
|
||||
using (var reader = new BinaryReader(stream))
|
||||
{
|
||||
classIdToName = ReadClassNames(reader, fieldNames, numberOfClasses);
|
||||
}
|
||||
}
|
||||
|
||||
var classIdToName = ReadClassIdToName(info, offsets, fieldNames, numberOfClasses);
|
||||
var numberOfEmbeddedObjects = (offsets[4] - offsets[3] - 8) / 16;
|
||||
Dictionary<int, Dictionary<int, int>> embeddedObjectPositionsToValues = null;
|
||||
using (var stream = new MemoryStream(info, offsets[3], offsets[4] - offsets[3]))
|
||||
{
|
||||
using (var reader = new BinaryReader(stream))
|
||||
{
|
||||
embeddedObjectPositionsToValues =
|
||||
ReadEmbeddedObjectPositionsToValuesMapping(reader, numberOfEmbeddedObjects);
|
||||
}
|
||||
}
|
||||
|
||||
var embeddedObjectPositionsToValues = ReadEmbeddedObjectPositionsToValues(info, offsets, numberOfEmbeddedObjects);
|
||||
var numberOfObjects = ((offsets[5] - offsets[4]) / 24) - 1;
|
||||
Dictionary<int, ObjectClassInformation> objectClasses = null;
|
||||
using (var stream = new MemoryStream(info, offsets[4], offsets[5] - offsets[4]))
|
||||
{
|
||||
using (var reader = new BinaryReader(stream))
|
||||
{
|
||||
objectClasses = ReadObjectClasses(reader, numberOfObjects);
|
||||
}
|
||||
}
|
||||
|
||||
var objectClasses = ReadObjectClassInformations(info, offsets, numberOfObjects);
|
||||
var numberOfObjectPositions = objectClasses.Values.Count(x => x.ObjectPosition != 0);
|
||||
|
||||
Dictionary<int, Dictionary<int, int>> objectPositionsToValues = null;
|
||||
using (var stream = new MemoryStream(info, offsets[5], offsets[6] - offsets[5]))
|
||||
{
|
||||
using (var reader = new BinaryReader(stream))
|
||||
{
|
||||
objectPositionsToValues = ReadObjectPositionsToValuesMapping(reader, numberOfObjectPositions);
|
||||
}
|
||||
}
|
||||
|
||||
var objectPositionsToValues = ReadObjectPositionsToValues(info, offsets, numberOfObjectPositions);
|
||||
var (classInformation, objectInformation) =
|
||||
GatherClassAndObjectInformation(
|
||||
classIdToName,
|
||||
@ -89,7 +51,6 @@ namespace MatFileHandler
|
||||
objectClasses,
|
||||
objectPositionsToValues,
|
||||
embeddedObjectPositionsToValues);
|
||||
|
||||
var allFields = objectInformation.Values.SelectMany(obj => obj.FieldLinks.Values);
|
||||
var data = new Dictionary<int, IArray>();
|
||||
foreach (var i in allFields)
|
||||
@ -100,7 +61,44 @@ namespace MatFileHandler
|
||||
return new SubsystemData(classInformation, objectInformation, data);
|
||||
}
|
||||
|
||||
private static (Dictionary<int, SubsystemData.ClassInfo>, Dictionary<int, SubsystemData.ObjectInfo>)
|
||||
private static Dictionary<int, Dictionary<int, int>> ReadObjectPositionsToValues(byte[] info, int[] offsets, int numberOfObjectPositions)
|
||||
{
|
||||
using var stream = new MemoryStream(info, offsets[5], offsets[6] - offsets[5]);
|
||||
using var reader = new BinaryReader(stream);
|
||||
return ReadObjectPositionsToValuesMapping(reader, numberOfObjectPositions);
|
||||
}
|
||||
|
||||
private static Dictionary<int, ObjectClassInformation> ReadObjectClassInformations(byte[] info, int[] offsets, int numberOfObjects)
|
||||
{
|
||||
using var stream = new MemoryStream(info, offsets[4], offsets[5] - offsets[4]);
|
||||
using var reader = new BinaryReader(stream);
|
||||
return ReadObjectClasses(reader, numberOfObjects);
|
||||
}
|
||||
|
||||
private static Dictionary<int, Dictionary<int, int>> ReadEmbeddedObjectPositionsToValues(byte[] info, int[] offsets, int numberOfEmbeddedObjects)
|
||||
{
|
||||
using var stream = new MemoryStream(info, offsets[3], offsets[4] - offsets[3]);
|
||||
using var reader = new BinaryReader(stream);
|
||||
return ReadEmbeddedObjectPositionsToValuesMapping(reader, numberOfEmbeddedObjects);
|
||||
}
|
||||
|
||||
private static Dictionary<int, string> ReadClassIdToName(byte[] info, int[] offsets, string[] fieldNames, int numberOfClasses)
|
||||
{
|
||||
using var stream = new MemoryStream(info, offsets[2], offsets[3] - offsets[2]);
|
||||
using var reader = new BinaryReader(stream);
|
||||
return ReadClassNames(reader, fieldNames, numberOfClasses);
|
||||
}
|
||||
|
||||
private static List<RawVariable> ReadRawVariables(byte[] bytes, SubsystemData subsystemData)
|
||||
{
|
||||
using var stream = new MemoryStream(bytes);
|
||||
using var reader = new BinaryReader(stream);
|
||||
reader.ReadBytes(8);
|
||||
return MatFileReader.ReadRawVariables(reader, -1, subsystemData);
|
||||
}
|
||||
|
||||
private static (Dictionary<int, SubsystemData.ClassInfo> classInfos,
|
||||
Dictionary<int, SubsystemData.ObjectInfo> objectInfos)
|
||||
GatherClassAndObjectInformation(
|
||||
Dictionary<int, string> classIdToName,
|
||||
string[] fieldNames,
|
||||
@ -318,7 +316,7 @@ namespace MatFileHandler
|
||||
string.Empty,
|
||||
string.Empty,
|
||||
dimensions,
|
||||
array as DataElement,
|
||||
uintArray,
|
||||
indexToObjectId,
|
||||
classIndex,
|
||||
subsystemData);
|
||||
|
@ -18,25 +18,34 @@ namespace MatFileHandler
|
||||
/// <param name="array">Source table object.</param>
|
||||
public TableAdapter(IArray array)
|
||||
{
|
||||
matObject = array as IMatObject;
|
||||
if (matObject?.ClassName != "table")
|
||||
matObject = array as IMatObject
|
||||
?? throw new HandlerException("Table adapter must be initialized with a MATLAB object.");
|
||||
if (matObject.ClassName != "table")
|
||||
{
|
||||
throw new ArgumentException("The object provided is not a table.");
|
||||
}
|
||||
|
||||
var cellArray = matObject["varnames"] as ICellArray;
|
||||
var cellArray = matObject["varnames"] as ICellArray
|
||||
?? throw new HandlerException("Table variable names must be in a cell array.");
|
||||
VariableNames = Enumerable
|
||||
.Range(0, cellArray.Count)
|
||||
.Select(i => (cellArray[i] as ICharArray).String)
|
||||
.Select(i =>
|
||||
(cellArray[i] as ICharArray ??
|
||||
throw new HandlerException("Variable name must be a char array.")).String)
|
||||
.ToArray();
|
||||
NumberOfVariables = VariableNames.Length;
|
||||
var props = matObject["props"] as IStructureArray;
|
||||
Description = (props["Description"] as ICharArray).String;
|
||||
NumberOfRows = (int)matObject["nrows"].ConvertToDoubleArray()[0];
|
||||
var rowNamesArrays = matObject["rownames"] as ICellArray;
|
||||
var props = matObject["props"] as IStructureArray
|
||||
?? throw new HandlerException("Table properties must be a structure array.");
|
||||
Description = (props["Description"] as ICharArray
|
||||
?? throw new HandlerException("Table description must be a char array.")).String;
|
||||
NumberOfRows = (int)(matObject["nrows"].ConvertToDoubleArray()
|
||||
?? throw new HandlerException("Cannot find number of rows in a table."))[0];
|
||||
var rowNamesArrays = matObject["rownames"] as ICellArray
|
||||
?? throw new HandlerException("Table row names must be a cell array.");
|
||||
RowNames = Enumerable
|
||||
.Range(0, rowNamesArrays.Count)
|
||||
.Select(i => (cellArray[i] as ICharArray).String)
|
||||
.Select(i => (cellArray[i] as ICharArray
|
||||
?? throw new HandlerException("Each table row name must be a char array.")).String)
|
||||
.ToArray();
|
||||
}
|
||||
|
||||
@ -66,7 +75,7 @@ namespace MatFileHandler
|
||||
public string[] VariableNames { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets all the data for a given variable
|
||||
/// Gets all the data for a given variable.
|
||||
/// </summary>
|
||||
/// <param name="variableName">Variable name.</param>
|
||||
/// <returns>All data associated with the variable.</returns>
|
||||
@ -83,7 +92,8 @@ namespace MatFileHandler
|
||||
throw new IndexOutOfRangeException($"Variable '{variableName}' not found.");
|
||||
}
|
||||
|
||||
var data = matObject["data"] as ICellArray;
|
||||
var data = matObject["data"] as ICellArray
|
||||
?? throw new HandlerException("Table data must be stored in a cell array.");
|
||||
return data[index];
|
||||
}
|
||||
}
|
||||
|
@ -4,12 +4,17 @@
|
||||
# https://docs.microsoft.com/azure/devops/pipelines/languages/dotnet-core
|
||||
|
||||
pool:
|
||||
vmImage: 'vs2017-win2016'
|
||||
vmImage: 'windows-latest'
|
||||
|
||||
variables:
|
||||
buildConfiguration: 'Release'
|
||||
|
||||
steps:
|
||||
- task: UseDotNet@2
|
||||
displayName: 'Use .NET Core SDK 3.x'
|
||||
inputs:
|
||||
version: 3.x
|
||||
|
||||
- script: dotnet build --configuration $(buildConfiguration)
|
||||
displayName: 'dotnet build $(buildConfiguration)'
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user