diff --git a/VectoCommon/VectoCommon/Models/GearboxType.cs b/VectoCommon/VectoCommon/Models/GearboxType.cs index d3af018a83094a540ed986900ff714ed225c8720..031f76cb43e4b349955aa0beb113806f42ae7585 100644 --- a/VectoCommon/VectoCommon/Models/GearboxType.cs +++ b/VectoCommon/VectoCommon/Models/GearboxType.cs @@ -30,6 +30,7 @@ */ using System; +using System.Diagnostics; using System.Diagnostics.CodeAnalysis; using TUGraz.VectoCommon.Utils; @@ -66,16 +67,19 @@ namespace TUGraz.VectoCommon.Models } } + [DebuggerStepThrough] public static string ShortName(this GearboxType type) { return type.ToString(); } + [DebuggerStepThrough] public static bool AutomaticTransmission(this GearboxType type) { return type == GearboxType.ATPowerSplit || type == GearboxType.ATSerial; } + [DebuggerStepThrough] public static bool ManualTransmission(this GearboxType type) { return type == GearboxType.MT || type == GearboxType.AMT; diff --git a/VectoCommon/VectoCommon/Utils/DoubleExtensionMethods.cs b/VectoCommon/VectoCommon/Utils/DoubleExtensionMethods.cs index 57684ac528cd3fb360efae0e70725d651bd5612f..871438e5422e6f73cf48377c2846cee9cb9fcdea 100644 --- a/VectoCommon/VectoCommon/Utils/DoubleExtensionMethods.cs +++ b/VectoCommon/VectoCommon/Utils/DoubleExtensionMethods.cs @@ -34,6 +34,7 @@ using System.Collections.Generic; using System.Diagnostics; using System.Globalization; using System.Linq; +using System.Runtime.CompilerServices; namespace TUGraz.VectoCommon.Utils { @@ -59,19 +60,22 @@ namespace TUGraz.VectoCommon.Utils /// <param name="other">The other.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> - [DebuggerHidden] + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static bool IsEqual(this double self, double other, double tolerance = Tolerance) { return Math.Abs(self - other) < tolerance; } - [DebuggerHidden] + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static bool IsRelativeEqual(this SI expected, SI actual, double toleranceFactor = ToleranceFactor) { return IsRelativeEqual(expected.Value(), actual.Value(), toleranceFactor: toleranceFactor); } - [DebuggerHidden] + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static bool IsRelativeEqual(this double expected, double actual, double toleranceFactor = DoubleExtensionMethods.ToleranceFactor) { @@ -90,7 +94,8 @@ namespace TUGraz.VectoCommon.Utils /// <param name="other">The other.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> - [DebuggerHidden] + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static bool IsSmaller(this double self, double other, double tolerance = Tolerance) { return self < other - tolerance; @@ -103,6 +108,8 @@ namespace TUGraz.VectoCommon.Utils /// <param name="other">The other.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static bool IsSmallerOrEqual(this double self, double other, double tolerance = Tolerance) { return self <= other + tolerance; @@ -115,6 +122,8 @@ namespace TUGraz.VectoCommon.Utils /// <param name="other">The other.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static bool IsGreater(this double self, double other, double tolerance = Tolerance) { return self > other + tolerance; @@ -127,6 +136,8 @@ namespace TUGraz.VectoCommon.Utils /// <param name="other">The other.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static bool IsGreaterOrEqual(this double self, double other, double tolerance = Tolerance) { return self >= other - tolerance; @@ -137,17 +148,39 @@ namespace TUGraz.VectoCommon.Utils /// </summary> /// <param name="self">The self.</param> /// <param name="tolerance">The tolerance.</param> - /// <returns></returns> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static bool IsPositive(this double self, double tolerance = Tolerance) { return self >= -tolerance; } + /// <summary> + /// Checks if a value is between min and max (min <= value <= max) + /// </summary> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static bool IsBetween(this double self, double min, double max) + { + return min <= self && self <= max; + } + + /// <summary> + /// Checks if a value is between min and max (min <= value <= max) + /// </summary> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static bool IsBetween(this double self, SI min, SI max) + { + return min <= self && self <= max; + } + /// <summary> /// Converts the double-value from RPM (rounds per minute) to the SI Unit PerSecond. /// </summary> /// <param name="self"></param> - /// <returns></returns> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static PerSecond RPMtoRad(this double self) { return SI<PerSecond>(self * 2 * Math.PI / 60.0); @@ -156,8 +189,8 @@ namespace TUGraz.VectoCommon.Utils /// <summary> /// Converts the double-value from RPM (rounds per minute) to the SI Unit PerSecond. /// </summary> - /// <param name="self"></param> - /// <returns></returns> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static PerSecond RPMtoRad(this float self) { return SI<PerSecond>(self * 2 * Math.PI / 60.0); @@ -166,25 +199,29 @@ namespace TUGraz.VectoCommon.Utils /// <summary> /// Converts the value from rounds per minute to the SI Unit PerSecond /// </summary> - /// <param name="self"></param> - /// <returns></returns> - [DebuggerHidden] + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static PerSecond RPMtoRad(this int self) { return SI<PerSecond>(self * 2.0 * Math.PI / 60.0); } + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static MeterPerSecond KMPHtoMeterPerSecond(this double self) { return SI<MeterPerSecond>(self / 3.6); } - [DebuggerHidden] + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static MeterPerSecond KMPHtoMeterPerSecond(this int self) { return SI<MeterPerSecond>(self / 3.6); } + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static double ToDegree(this double self) { return self * 180.0 / Math.PI; @@ -193,6 +230,8 @@ namespace TUGraz.VectoCommon.Utils /// <summary> /// Creates an SI object for the number (unit-less: [-]). /// </summary> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static SI SI(this double value) { return new SI(value); @@ -201,17 +240,22 @@ namespace TUGraz.VectoCommon.Utils /// <summary> /// Creates an templated SI object for the number. /// </summary> - [DebuggerHidden] + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static T SI<T>(this double value) where T : SIBase<T> { return SIBase<T>.Create(value); } + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static IEnumerable<T> SI<T>(this IEnumerable<double> self) where T : SIBase<T> { return self.Select(x => x.SI<T>()); } + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static string ToGUIFormat(this double self) { return self.ToString(CultureInfo.InvariantCulture); @@ -220,7 +264,8 @@ namespace TUGraz.VectoCommon.Utils public static class FloatExtensionMethods { - [DebuggerHidden] + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static T SI<T>(this float value) where T : SIBase<T> { return SIBase<T>.Create(value); @@ -229,6 +274,8 @@ namespace TUGraz.VectoCommon.Utils public static class IntegerExtensionMethods { + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static string ToGUIFormat(this int self) { return self.ToString(); diff --git a/VectoCommon/VectoCommon/Utils/EnumerableExtensionMethods.cs b/VectoCommon/VectoCommon/Utils/EnumerableExtensionMethods.cs index 666526060e53e3b4a7479f161d1c7d9021159985..e1f3fd2d4ccf8db596b45b0c5f4fd57eb5db8bf0 100644 --- a/VectoCommon/VectoCommon/Utils/EnumerableExtensionMethods.cs +++ b/VectoCommon/VectoCommon/Utils/EnumerableExtensionMethods.cs @@ -225,6 +225,11 @@ namespace TUGraz.VectoCommon.Utils } } + public static IEnumerable<Tuple<TSource, TSource>> Pairwise<TSource>(this IEnumerable<TSource> source) + { + return Pairwise(source, Tuple.Create); + } + /// <summary> /// Repeats the element and returns an Enumerable. /// </summary> diff --git a/VectoCommon/VectoCommon/Utils/SI.cs b/VectoCommon/VectoCommon/Utils/SI.cs index a3ea8a013314f5b4cd14ae57ed4d8bff7b6c2808..0a726e2f8e780588583f8b71094609b6441bbcbd 100644 --- a/VectoCommon/VectoCommon/Utils/SI.cs +++ b/VectoCommon/VectoCommon/Utils/SI.cs @@ -826,6 +826,7 @@ namespace TUGraz.VectoCommon.Utils /// Creates the specified special SI object. /// </summary> /// <param name="val">The value of the SI object.</param> + [DebuggerStepThrough] public static T Create(double val) { if (val == 0) { @@ -1907,16 +1908,16 @@ namespace TUGraz.VectoCommon.Utils if (Denominator.Any()) { if (Numerator.Any()) { return string.Concat( - Numerator.GroupBy(x => x) - .Select(x => x.Count() == 1 ? x.Key.ToString() : string.Format("{0}^{1}", x.Key, x.Count()))) + Numerator.GroupBy(x => x) + .Select(x => x.Count() == 1 ? x.Key.ToString() : string.Format("{0}^{1}", x.Key, x.Count()))) + "/" + string.Concat( Denominator.GroupBy(x => x) .Select(x => x.Count() == 1 ? x.Key.ToString() : string.Format("{0}^{1}", x.Key, x.Count()))); } return "1/" + string.Concat( - Denominator.GroupBy(x => x) - .Select(x => x.Count() == 1 ? x.Key.ToString() : string.Format("{0}^{1}", x.Key, x.Count()))); + Denominator.GroupBy(x => x) + .Select(x => x.Count() == 1 ? x.Key.ToString() : string.Format("{0}^{1}", x.Key, x.Count()))); } if (Numerator.Any()) { @@ -2092,6 +2093,7 @@ namespace TUGraz.VectoCommon.Utils /// <param name="si">The si.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> + [DebuggerStepThrough] public bool IsGreater(SI si, double tolerance) { if (!HasEqualUnit(si)) { @@ -2107,6 +2109,7 @@ namespace TUGraz.VectoCommon.Utils /// <param name="si">The si.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> + [DebuggerStepThrough] public bool IsGreaterOrEqual(SI si, SI tolerance = null) { if (!HasEqualUnit(si)) { @@ -2125,6 +2128,7 @@ namespace TUGraz.VectoCommon.Utils /// <param name="val">The value.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> + [DebuggerStepThrough] public bool IsSmaller(double val, double tolerance = DoubleExtensionMethods.Tolerance) { return Val.IsSmaller(val, tolerance); @@ -2136,6 +2140,7 @@ namespace TUGraz.VectoCommon.Utils /// <param name="val">The value.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> + [DebuggerStepThrough] public bool IsSmallerOrEqual(double val, double tolerance = DoubleExtensionMethods.Tolerance) { return Val.IsSmallerOrEqual(val, tolerance); @@ -2147,6 +2152,7 @@ namespace TUGraz.VectoCommon.Utils /// <param name="val">The value.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> + [DebuggerStepThrough] public bool IsGreater(double val, double tolerance = DoubleExtensionMethods.Tolerance) { return Val.IsGreater(val, tolerance); @@ -2158,6 +2164,7 @@ namespace TUGraz.VectoCommon.Utils /// <param name="val">The value.</param> /// <param name="tolerance">The tolerance.</param> /// <returns></returns> + [DebuggerStepThrough] public bool IsGreaterOrEqual(double val, double tolerance = DoubleExtensionMethods.Tolerance) { return Val.IsGreaterOrEqual(val, tolerance); diff --git a/VectoCommon/VectoCommon/Utils/VectoMath.cs b/VectoCommon/VectoCommon/Utils/VectoMath.cs index 3f801863df03a528c33ed2908dd7a658b35ab3fc..8281b76ee2638387435ccedb97d463172c7ede48 100644 --- a/VectoCommon/VectoCommon/Utils/VectoMath.cs +++ b/VectoCommon/VectoCommon/Utils/VectoMath.cs @@ -55,23 +55,68 @@ namespace TUGraz.VectoCommon.Utils /// <param name="y2">Second Value on the Y-Axis.</param> /// <param name="xint">Value on the X-Axis, for which the Y-Value should be interpolated.</param> /// <returns></returns> + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static TResult Interpolate<T, TResult>(T x1, T x2, TResult y1, TResult y2, T xint) where T : SI where TResult : SIBase<TResult> { return Interpolate(x1.Value(), x2.Value(), y1.Value(), y2.Value(), xint.Value()).SI<TResult>(); } + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static TResult Interpolate<TInput, T, TResult>(this Tuple<TInput, TInput> self, Func<TInput, T> x, + Func<TInput, TResult> y, T xInterpolate) + where T : SIBase<T> + where TResult : SIBase<TResult> + { + return Interpolate(x(self.Item1).Value(), x(self.Item2).Value(), y(self.Item1).Value(), y(self.Item2).Value(), + xInterpolate.Value()).SI<TResult>(); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static TResult Interpolate<TInput, TResult>(this Tuple<TInput, TInput> self, Func<TInput, double> x, + Func<TInput, TResult> y, double xInterpolate) + where TResult : SIBase<TResult> + { + return + Interpolate(x(self.Item1), x(self.Item2), y(self.Item1).Value(), y(self.Item2).Value(), xInterpolate).SI<TResult>(); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static TResult Interpolate<TInput, TResult>(this IEnumerable<TInput> self, Func<TInput, double> x, + Func<TInput, TResult> y, double xInterpolate) + where TResult : SIBase<TResult> + { + return self.GetSection(elem => x(elem) < xInterpolate).Interpolate(x, y, xInterpolate); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static double Interpolate<TInput>(this IEnumerable<TInput> self, Func<TInput, double> x, + Func<TInput, double> y, double xInterpolate) + { + return self.GetSection(elem => x(elem) < xInterpolate).Interpolate(x, y, xInterpolate); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static double Interpolate<TInput>(this Tuple<TInput, TInput> self, Func<TInput, double> x, + Func<TInput, double> y, double xInterpolate) + { + return Interpolate(x(self.Item1), x(self.Item2), y(self.Item1), y(self.Item2), xInterpolate); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static double Interpolate<T>(T x1, T x2, double y1, double y2, T xint) where T : SI { return Interpolate(x1.Value(), x2.Value(), y1, y2, xint.Value()); } + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static TResult Interpolate<TResult>(double x1, double x2, TResult y1, TResult y2, double xint) where TResult : SIBase<TResult> { return Interpolate(x1, x2, y1.Value(), y2.Value(), xint).SI<TResult>(); } + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static double Interpolate(Point p1, Point p2, double x) { return Interpolate(p1.X, p2.X, p1.Y, p2.Y, x); @@ -80,6 +125,7 @@ namespace TUGraz.VectoCommon.Utils /// <summary> /// Linearly interpolates a value between two points. /// </summary> + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static double Interpolate(double x1, double x2, double y1, double y2, double xint) { return (xint - x1) * (y2 - y1) / (x2 - x1) + y1; @@ -88,6 +134,8 @@ namespace TUGraz.VectoCommon.Utils /// <summary> /// Returns the absolute value. /// </summary> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static SI Abs(SI si) { return si.Abs(); @@ -96,6 +144,8 @@ namespace TUGraz.VectoCommon.Utils /// <summary> /// Returns the minimum of two values. /// </summary> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static T Min<T>(T c1, T c2) where T : IComparable { return c1.CompareTo(c2) <= 0 ? c1 : c2; @@ -104,59 +154,67 @@ namespace TUGraz.VectoCommon.Utils /// <summary> /// Returns the maximum of two values. /// </summary> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static T Max<T>(T c1, T c2) where T : IComparable { return c1.CompareTo(c2) >= 0 ? c1 : c2; } + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static T Max<T>(T c1, T c2, T c3) where T : IComparable { return Max(Max(c1, c2), c3); } - public static T Limit<T>(this T value, T lowerBound, T upperBound) where T : IComparable + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static T LimitTo<T>(this T value, T lowerBound, T upperBound) where T : IComparable { if (lowerBound.CompareTo(upperBound) > 0) { throw new VectoException( - "VectoMath.Limit: lowerBound must not be greater than upperBound. lowerBound: {0}, upperBound: {1}", lowerBound, + "VectoMath.LimitTo: lowerBound must not be greater than upperBound. lowerBound: {0}, upperBound: {1}", lowerBound, upperBound); } if (value.CompareTo(upperBound) > 0) { return upperBound; } + if (value.CompareTo(lowerBound) < 0) { return lowerBound; } + return value; } /// <summary> - /// converts the given inclination in percent (0-1+) into Radians + /// converts the given inclination in percent (0-1+) into Radians /// </summary> - /// <param name="inclinationPercent"></param> - /// <returns></returns> + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static Radian InclinationToAngle(double inclinationPercent) { return Math.Atan(inclinationPercent).SI<Radian>(); } - public static List<double> QuadraticEquationSolver(double a, double b, double c) + public static double[] QuadraticEquationSolver(double a, double b, double c) { - var retVal = new List<double>(); var d = b * b - 4 * a * c; + // no real solution if (d < 0) { - return retVal; - } else if (d > 0) { - // two solutions possible - retVal.Add((-b + Math.Sqrt(d)) / (2 * a)); - retVal.Add((-b - Math.Sqrt(d)) / (2 * a)); - } else { - // only one solution possible - retVal.Add(-b / (2 * a)); + return new double[0]; } - return retVal; + + if (d > 0) { + // two solutions + return new[] { (-b + Math.Sqrt(d)) / (2 * a), (-b - Math.Sqrt(d)) / (2 * a) }; + } + + // one real solution + return new[] { -b / (2 * a) }; } public static Point Intersect(Edge line1, Edge line2) @@ -221,10 +279,10 @@ namespace TUGraz.VectoCommon.Utils // we need to accelerate / decelerate. solve quadratic equation... // ds = acceleration / 2 * dt^2 + currentSpeed * dt => solve for dt - var solutions = VectoMath.QuadraticEquationSolver(acceleration.Value() / 2.0, currentSpeed.Value(), + var solutions = QuadraticEquationSolver(acceleration.Value() / 2.0, currentSpeed.Value(), -ds.Value()); - if (solutions.Count == 0) { + if (solutions.Length == 0) { // no real-valued solutions: acceleration is so negative that vehicle stops already before the required distance can be reached. // adapt ds to the halting-point. // t = v / a @@ -256,12 +314,14 @@ namespace TUGraz.VectoCommon.Utils return retVal; } + [DebuggerStepThrough] + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static T Ceiling<T>(T si) where T : SIBase<T> { return Math.Ceiling(si.Value()).SI<T>(); } - public static List<double> CubicEquationSolver(double a, double b, double c, double d) + public static double[] CubicEquationSolver(double a, double b, double c, double d) { var solutions = new List<double>(); if (a.IsEqual(0, 1e-12)) { @@ -280,7 +340,7 @@ namespace TUGraz.VectoCommon.Utils solutions.Add(p * Math.Cos((phi + 2 * i * Math.PI) / 3.0) - w); } } else { - // only one real solution + // one real solution discriminant = Math.Sqrt(discriminant); solutions.Add(Cbrt(q + discriminant) + Cbrt(q - discriminant) - w); } @@ -293,7 +353,7 @@ namespace TUGraz.VectoCommon.Utils } } solutions.Sort(); - return solutions; + return solutions.ToArray(); } private static double Cbrt(double x) @@ -336,27 +396,11 @@ namespace TUGraz.VectoCommon.Utils return new Point(p1.X * scalar, p1.Y * scalar, p1.Z * scalar); } - /// <summary> - /// - /// </summary> - /// <param name="scalar"></param> - /// <param name="p1"></param> - /// <returns></returns> public static Point operator *(double scalar, Point p1) { return p1 * scalar; } - /// <summary> - /// Calculates cross product between two 3d-vectors. - /// </summary> - /// <param name="other"></param> - /// <returns></returns> - public Point Cross(Point other) - { - return new Point(Y * other.Z - Z * other.Y, Z * other.X - X * other.Z, X * other.Y - Y * other.X); - } - /// <summary> /// Returns perpendicular vector for xy-components of this point. P = (-Y, X) /// </summary> @@ -422,14 +466,6 @@ namespace TUGraz.VectoCommon.Utils public readonly double Z; public readonly double W; - public Plane(double x, double y, double z, double w) - { - X = x; - Y = y; - Z = z; - W = w; - } - public Plane(Triangle tr) { var abX = tr.P2.X - tr.P1.X; @@ -466,13 +502,8 @@ namespace TUGraz.VectoCommon.Utils } /// <summary> - /// Barycentric Technique: http://www.blackpawn.com/texts/pointinpoly/default.html + /// Check if Point is inside of Triangle. Barycentric Technique: http://www.blackpawn.com/texts/pointinpoly/default.html /// </summary> - /// <param name="x"></param> - /// <param name="y"></param> - /// <param name="exact"></param> - /// <returns></returns> - [MethodImpl(MethodImplOptions.AggressiveInlining)] public bool IsInside(double x, double y, bool exact) { var smallerY = y - DoubleExtensionMethods.Tolerance; @@ -530,17 +561,6 @@ namespace TUGraz.VectoCommon.Utils var result = p0Square * det12 + p1Square * det20 + p2Square * det01; return result > 0; - - //double[,] m = { { P1.X - p.X, P1.Y - p.Y, (P1.X * P1.X - p.X*p.X) + (P1.Y * P1.Y - p.Y*p.Y) }, - // { P2.X - p.X, P2.Y - p.Y, (P2.X * P2.X - p.X*p.X) + (P2.Y * P2.Y - p.Y*p.Y) }, - // { P3.X - p.X, P3.Y - p.Y, (P3.X * P3.X - p.X*p.X) + (P3.Y * P3.Y - p.Y*p.Y) } }; - //var det = m[0, 0] * m[1, 1] * m[2, 2] - // + m[0, 1] * m[1, 2] * m[2, 0] - // + m[0, 2] * m[1, 0] * m[2, 1] - // - m[0, 0] * m[1, 2] * m[2, 1] - // - m[0, 1] * m[1, 0] * m[2, 2] - // - m[0, 2] * m[1, 1] * m[2, 0]; - //return det > 0; } public bool Contains(Point p) @@ -553,7 +573,7 @@ namespace TUGraz.VectoCommon.Utils return Contains(t.P1) || Contains(t.P2) || Contains(t.P3); } - public Edge[] GetEdges() + public IEnumerable<Edge> GetEdges() { return new[] { new Edge(P1, P2), new Edge(P2, P3), new Edge(P3, P1) }; } diff --git a/VectoCore/VectoCore/InputData/AuxiliaryFileHelper.cs b/VectoCore/VectoCore/InputData/AuxiliaryFileHelper.cs new file mode 100644 index 0000000000000000000000000000000000000000..e92f4417d065cbb086becdd4b795f1561dc0163e --- /dev/null +++ b/VectoCore/VectoCore/InputData/AuxiliaryFileHelper.cs @@ -0,0 +1,43 @@ +using System.Data; +using System.IO; +using System.Text; +using TUGraz.VectoCommon.Exceptions; +using TUGraz.VectoCommon.Utils; +using TUGraz.VectoCore.InputData.Impl; +using TUGraz.VectoCore.InputData.Reader.ComponentData; +using TUGraz.VectoCore.Utils; + +namespace TUGraz.VectoCore.InputData +{ + public static class AuxiliaryFileHelper + { + public static void FillAuxiliaryDataInputData(AuxiliaryDataInputData auxData, string auxFile) + { + try { + var stream = new StreamReader(auxFile); + stream.ReadLine(); // skip header "Transmission ration to engine rpm [-]" + auxData.TransmissionRatio = stream.ReadLine().IndulgentParse(); + stream.ReadLine(); // skip header "Efficiency to engine [-]" + auxData.EfficiencyToEngine = stream.ReadLine().IndulgentParse(); + stream.ReadLine(); // skip header "Efficiency auxiliary to supply [-]" + auxData.EfficiencyToSupply = stream.ReadLine().IndulgentParse(); + + var table = VectoCSVFile.ReadStream(new MemoryStream(Encoding.UTF8.GetBytes(stream.ReadToEnd())), source: auxFile); + foreach (DataRow row in table.Rows) { + if (AuxiliaryDataReader.HeaderIsValid(table.Columns)) { + row[AuxiliaryDataReader.Fields.MechPower] = + row.ParseDouble(AuxiliaryDataReader.Fields.MechPower).SI().Kilo.Watt.Value(); + row[AuxiliaryDataReader.Fields.SupplyPower] = + row.ParseDouble(AuxiliaryDataReader.Fields.SupplyPower).SI().Kilo.Watt.Value(); + } else { + row[1] = row.ParseDouble(1).SI().Kilo.Watt.Value(); + row[2] = row.ParseDouble(2).SI().Kilo.Watt.Value(); + } + } + auxData.DemandMap = table; + } catch (FileNotFoundException e) { + throw new VectoException("Auxiliary file not found: " + auxFile, e); + } + } + } +} \ No newline at end of file diff --git a/VectoCore/VectoCore/InputData/FileIO/JSON/JSONInputData.cs b/VectoCore/VectoCore/InputData/FileIO/JSON/JSONInputData.cs index 5a2d79a6207dd630db04534d623fbf85d75f791a..553649a3ee75d0714655668cc8f1af2edc18f8dd 100644 --- a/VectoCore/VectoCore/InputData/FileIO/JSON/JSONInputData.cs +++ b/VectoCore/VectoCore/InputData/FileIO/JSON/JSONInputData.cs @@ -32,10 +32,8 @@ using Newtonsoft.Json.Linq; using System; using System.Collections.Generic; -using System.Data; using System.IO; using System.Linq; -using System.Text; using TUGraz.VectoCommon.Exceptions; using TUGraz.VectoCommon.InputData; using TUGraz.VectoCommon.Models; @@ -477,7 +475,7 @@ namespace TUGraz.VectoCore.InputData.FileIO.JSON var acceleration = Body[JsonKeys.DriverData_AccelerationCurve]; if (acceleration == null || EmptyOrInvalidFileName(acceleration.Value<string>())) { return null; -// throw new VectoException("AccelerationCurve (VACC) required"); + // throw new VectoException("AccelerationCurve (VACC) required"); } try { return ReadTableData(acceleration.Value<string>(), "DriverAccelerationCurve", true); @@ -556,14 +554,8 @@ namespace TUGraz.VectoCore.InputData.FileIO.JSON if (auxFile == null || EmptyOrInvalidFileName(auxFile.Value<string>())) { continue; } - var stream = new StreamReader(Path.Combine(BasePath, auxFile.Value<string>())); - stream.ReadLine(); // skip header "Transmission ration to engine rpm [-]" - auxData.TransmissionRatio = stream.ReadLine().IndulgentParse(); - stream.ReadLine(); // skip header "Efficiency to engine [-]" - auxData.EfficiencyToEngine = stream.ReadLine().IndulgentParse(); - stream.ReadLine(); // skip header "Efficiency auxiliary to supply [-]" - auxData.EfficiencyToSupply = stream.ReadLine().IndulgentParse(); - auxData.DemandMap = VectoCSVFile.ReadStream(new MemoryStream(Encoding.UTF8.GetBytes(stream.ReadToEnd())), source: Path.Combine(BasePath, auxFile.Value<string>())); + + AuxiliaryFileHelper.FillAuxiliaryDataInputData(auxData, Path.Combine(BasePath, auxFile.Value<string>())); } return retVal; } @@ -635,14 +627,7 @@ namespace TUGraz.VectoCore.InputData.FileIO.JSON if (auxFile == null || EmptyOrInvalidFileName(auxFile.Value<string>())) { continue; } - var stream = new StreamReader(Path.Combine(BasePath, auxFile.Value<string>())); - stream.ReadLine(); // skip header "Transmission ration to engine rpm [-]" - auxData.TransmissionRatio = stream.ReadLine().IndulgentParse(); - stream.ReadLine(); // skip header "Efficiency to engine [-]" - auxData.EfficiencyToEngine = stream.ReadLine().IndulgentParse(); - stream.ReadLine(); // skip header "Efficiency auxiliary to supply [-]" - auxData.EfficiencyToSupply = stream.ReadLine().IndulgentParse(); - auxData.DemandMap = VectoCSVFile.ReadStream(new MemoryStream(Encoding.UTF8.GetBytes(stream.ReadToEnd())), source: Path.Combine(BasePath, auxFile.Value<string>())); + AuxiliaryFileHelper.FillAuxiliaryDataInputData(auxData, Path.Combine(BasePath, auxFile.Value<string>())); } return retVal; } diff --git a/VectoCore/VectoCore/InputData/Reader/ComponentData/AuxiliaryDataReader.cs b/VectoCore/VectoCore/InputData/Reader/ComponentData/AuxiliaryDataReader.cs index 191a65a37ced513c232765aa87f15595f12d20d6..980f91456fb7a9bf40087ac151855cd7de3fbb8d 100644 --- a/VectoCore/VectoCore/InputData/Reader/ComponentData/AuxiliaryDataReader.cs +++ b/VectoCore/VectoCore/InputData/Reader/ComponentData/AuxiliaryDataReader.cs @@ -56,36 +56,6 @@ namespace TUGraz.VectoCore.InputData.Reader.ComponentData return new AuxiliaryData(data.TransmissionRatio, data.EfficiencyToEngine, data.EfficiencyToSupply, map); } - /// <summary> - /// Reads the demand map from a file. - /// </summary> - /// <param name="fileName"></param> - /// <param name="id"></param> - /// <returns></returns> - public static AuxiliaryData ReadFromFile(string fileName, string id) - { - try { - using (var reader = new StreamReader(fileName)) { - reader.ReadLine(); // skip header "Transmission ration to engine rpm [-]" - var transmissionRatio = reader.ReadLine().IndulgentParse(); - reader.ReadLine(); // skip header "Efficiency to engine [-]" - var efficiencyToEngine = reader.ReadLine().IndulgentParse(); - reader.ReadLine(); // skip header "Efficiency auxiliary to supply [-]" - var efficiencyToSupply = reader.ReadLine().IndulgentParse(); - - var m = new MemoryStream(Encoding.UTF8.GetBytes(reader.ReadToEnd())); - reader.Close(); - - var table = VectoCSVFile.ReadStream(m); - var map = ReadAuxMap(id, table); - - return new AuxiliaryData(transmissionRatio, efficiencyToEngine, efficiencyToSupply, map); - } - } catch (FileNotFoundException e) { - throw new VectoException("Auxiliary file not found: " + fileName, e); - } - } - private static DelaunayMap ReadAuxMap(string id, DataTable table) { var map = new DelaunayMap(id); @@ -103,9 +73,7 @@ namespace TUGraz.VectoCore.InputData.Reader.ComponentData { for (var i = 0; i < table.Rows.Count; i++) { var row = table.Rows[i]; - map.AddPoint(row.ParseDouble(0).RPMtoRad().Value(), - row.ParseDouble(1).SI().Kilo.Watt.Cast<Watt>().Value(), - row.ParseDouble(2).SI().Kilo.Watt.Cast<Watt>().Value()); + map.AddPoint(row.ParseDouble(0).RPMtoRad().Value(),row.ParseDouble(2),row.ParseDouble(1)); } } @@ -113,13 +81,11 @@ namespace TUGraz.VectoCore.InputData.Reader.ComponentData { for (var i = 0; i < table.Rows.Count; i++) { var row = table.Rows[i]; - map.AddPoint(row.ParseDouble(Fields.AuxSpeed).RPMtoRad().Value(), - row.ParseDouble(Fields.MechPower).SI().Kilo.Watt.Cast<Watt>().Value(), - row.ParseDouble(Fields.SupplyPower).SI().Kilo.Watt.Cast<Watt>().Value()); + map.AddPoint(row.ParseDouble(Fields.AuxSpeed).RPMtoRad().Value(),row.ParseDouble(Fields.SupplyPower),row.ParseDouble(Fields.MechPower)); } } - private static bool HeaderIsValid(DataColumnCollection columns) + public static bool HeaderIsValid(DataColumnCollection columns) { return columns.Contains(Fields.AuxSpeed) && columns.Contains(Fields.MechPower) && columns.Contains(Fields.SupplyPower); diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Data/Engine/EngineFullLoadCurve.cs b/VectoCore/VectoCore/Models/SimulationComponent/Data/Engine/EngineFullLoadCurve.cs index 1009b46606557d6567b2ed72d110b75ed3d4aecb..3445005d5c16f8a52adaf20ae0e969199d4fdae9 100644 --- a/VectoCore/VectoCore/Models/SimulationComponent/Data/Engine/EngineFullLoadCurve.cs +++ b/VectoCore/VectoCore/Models/SimulationComponent/Data/Engine/EngineFullLoadCurve.cs @@ -71,16 +71,13 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Engine return Formulas.TorqueToPower(DragLoadStationaryTorque(angularVelocity), angularVelocity); } - public CombustionEngineData EngineData { get; internal set; } - public Second PT1(PerSecond angularVelocity) { return PT1Data.Lookup(angularVelocity); } - /// <summary> /// Get the engine's preferred speed from the given full-load curve (i.e. Speed at 51% torque/speed-integral between idling and N95h.) /// </summary> @@ -105,7 +102,6 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Engine get { return _n95hSpeed ?? (_n95hSpeed = FindEngineSpeedForPower(0.95 * MaxPower).Last()); } } - public PerSecond LoSpeed { get { return _engineSpeedLo ?? (_engineSpeedLo = FindEngineSpeedForPower(0.55 * MaxPower).First()); } @@ -116,7 +112,6 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Engine get { return _engineSpeedHi ?? (_engineSpeedHi = FindEngineSpeedForPower(0.7 * MaxPower).Last()); } } - public NewtonMeter MaxLoadTorque { get { return FullLoadEntries.Max(x => x.TorqueFullLoad); } @@ -127,7 +122,6 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Engine get { return FullLoadEntries.Min(x => x.TorqueDrag); } } - private void ComputePreferredSpeed() { var maxArea = ComputeArea(EngineData.IdleSpeed, N95hSpeed); @@ -161,10 +155,10 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Engine // area = (M(n1) + M(n2))/2 * (n2 - n1) => solve for n2 var retVal = VectoMath.QuadraticEquationSolver(k.Value() / 2.0, d.Value(), (-k * p1.EngineSpeed * p1.EngineSpeed / 2 - p1.EngineSpeed * d - area).Value()); - if (retVal.Count == 0) { + if (retVal.Length == 0) { Log.Info("No real solution found for requested area: P: {0}, p1: {1}, p2: {2}", area, p1, p2); } - return retVal.First(x => x >= p1.EngineSpeed && x <= p2.EngineSpeed).SI<PerSecond>(); + return retVal.First(x => x.IsBetween(p1.EngineSpeed, p2.EngineSpeed)).SI<PerSecond>(); } private List<PerSecond> FindEngineSpeedForPower(Watt power) diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Data/Gearbox/TorqueConverterData.cs b/VectoCore/VectoCore/Models/SimulationComponent/Data/Gearbox/TorqueConverterData.cs index 41c075d9273d3073c42a33346c11175be38c779a..2a724025da679a91e2f87fc99250fd327ce51295 100644 --- a/VectoCore/VectoCore/Models/SimulationComponent/Data/Gearbox/TorqueConverterData.cs +++ b/VectoCore/VectoCore/Models/SimulationComponent/Data/Gearbox/TorqueConverterData.cs @@ -34,12 +34,13 @@ using System.Collections.Generic; using System.ComponentModel.DataAnnotations; using System.Linq; using TUGraz.VectoCommon.Exceptions; +using TUGraz.VectoCommon.Models; using TUGraz.VectoCommon.Utils; namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Gearbox { [CustomValidation(typeof(TorqueConverterData), "ValidateData")] - public class TorqueConverterData + public class TorqueConverterData : LoggingObject { protected List<TorqueConverterEntry> TorqueConverterEntries; @@ -95,34 +96,33 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Gearbox (mpNorm * mpNorm); var c = angularSpeedOut.Value() * angularSpeedOut.Value() * mpEdge.SlopeXY * muEdge.SlopeXY / (mpNorm * mpNorm) - torqueOut.Value(); - var sol = VectoMath.QuadraticEquationSolver(a, b, c); - var selected = sol.Where(x => x > min - && angularSpeedOut.Value() / x >= muEdge.P1.X && angularSpeedOut.Value() / x < muEdge.P2.X - && angularSpeedOut.Value() / x >= mpEdge.P1.X && angularSpeedOut.Value() / x < mpEdge.P2.X); - solutions.AddRange(selected); + solutions.AddRange(VectoMath.QuadraticEquationSolver(a, b, c).Where(x => { + var ratio = angularSpeedOut.Value() / x; + return x > min && muEdge.P1.X <= ratio && ratio < muEdge.P2.X; + })); } + if (solutions.Count == 0) { - throw new VectoException("No solution for input torque/input speed found! n_out: {0}, tq_out: {1}", angularSpeedOut, - torqueOut); + Log.Debug( + "TorqueConverterData::FindOperatingPoint No solution for input torque/input speed found! n_out: {0}, tq_out: {1}", + angularSpeedOut, torqueOut); } - var retVal = new List<TorqueConverterOperatingPoint>(); - foreach (var sol in solutions) { - var tmp = new TorqueConverterOperatingPoint { + return solutions.Select(sol => { + var s = sol.SI<PerSecond>(); + var mu = MuLookup(angularSpeedOut / s); + return new TorqueConverterOperatingPoint { OutTorque = torqueOut, OutAngularVelocity = angularSpeedOut, - InAngularVelocity = sol.SI<PerSecond>() + InAngularVelocity = s, + SpeedRatio = angularSpeedOut / s, + TorqueRatio = mu, + InTorque = torqueOut / mu, }; - tmp.SpeedRatio = angularSpeedOut / tmp.InAngularVelocity; - tmp.TorqueRatio = MuLookup(angularSpeedOut / tmp.InAngularVelocity); - tmp.InTorque = torqueOut / tmp.TorqueRatio; - retVal.Add(tmp); - } - return retVal; + }).ToList(); } - /// <summary> /// find an operating point for the torque converter /// @@ -139,30 +139,29 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Gearbox OutAngularVelocity = outAngularVelocity, SpeedRatio = outAngularVelocity.Value() / inAngularVelocity.Value(), }; - foreach (var segment in TorqueConverterEntries.Pairwise(Tuple.Create)) { - if (!(retVal.SpeedRatio >= segment.Item1.SpeedRatio) || !(retVal.SpeedRatio < segment.Item2.SpeedRatio)) { - continue; + + foreach (var segment in TorqueConverterEntries.Pairwise()) { + if (retVal.SpeedRatio.IsBetween(segment.Item1.SpeedRatio, segment.Item2.SpeedRatio)) { + var mpTorque = segment.Interpolate(x => x.SpeedRatio, y => y.Torque, retVal.SpeedRatio); + retVal.TorqueRatio = segment.Interpolate(x => x.SpeedRatio, y => y.TorqueRatio, retVal.SpeedRatio); + retVal.InTorque = mpTorque * (inAngularVelocity * inAngularVelocity / ReferenceSpeed / ReferenceSpeed).Value(); + retVal.OutTorque = retVal.InTorque * retVal.TorqueRatio; + return retVal; } - var mpTorque = VectoMath.Interpolate(segment.Item1.SpeedRatio, segment.Item2.SpeedRatio, segment.Item1.Torque, - segment.Item2.Torque, retVal.SpeedRatio); - retVal.TorqueRatio = VectoMath.Interpolate(segment.Item1.SpeedRatio, segment.Item2.SpeedRatio, - segment.Item1.TorqueRatio, segment.Item2.TorqueRatio, retVal.SpeedRatio); - retVal.InTorque = mpTorque * (inAngularVelocity * inAngularVelocity / ReferenceSpeed / ReferenceSpeed).Value(); - retVal.OutTorque = retVal.InTorque * retVal.TorqueRatio; - return retVal; } + + // No solution found. Throw Errror var nu = outAngularVelocity / inAngularVelocity; var nuMax = TorqueConverterEntries.Last().SpeedRatio; if (nu.IsGreater(nuMax)) { throw new VectoException( - "Torque Converter: Range of torque converter data is not sufficient. Needed nu: {0}, Got nu_max: {1}", nu, - nuMax); - } else { - throw new VectoException( - "Torque Converter: No solution for output speed/input speed found! n_out: {0}, n_in: {1}, nu: {2}, nu_max: {3}", - outAngularVelocity, inAngularVelocity, nu, nuMax); + "Torque Converter: Range of torque converter data is not sufficient. Needed nu: {0}, Got nu_max: {1}", nu, nuMax); } + + throw new VectoException( + "Torque Converter: No solution for output speed/input speed found! n_out: {0}, n_in: {1}, nu: {2}, nu_max: {3}", + outAngularVelocity, inAngularVelocity, nu, nuMax); } /// <summary> @@ -187,7 +186,6 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Gearbox } var solutions = new List<double>(); - // ReSharper disable once LoopCanBeConvertedToQuery foreach (var edge in TorqueConverterEntries.Pairwise( (p1, p2) => Edge.Create(new Point(p1.SpeedRatio, p1.Torque.Value()), new Point(p2.SpeedRatio, p2.Torque.Value())))) { var x = (referenceTorque - edge.OffsetXY) / edge.SlopeXY; @@ -206,9 +204,6 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Gearbox public TorqueConverterOperatingPoint FindOperatingPointForPowerDemand(Watt power, PerSecond prevInputSpeed, PerSecond nextOutputSpeed, KilogramSquareMeter inertia, Second dt) { - //var retVal = new TorqueConverterOperatingPoint { - // OutAngularVelocity = nextOutputSpeed - //}; var solutions = new List<double>(); var mpNorm = ReferenceSpeed.Value(); @@ -238,22 +233,12 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Data.Gearbox private double MuLookup(double speedRatio) { - int index; - TorqueConverterEntries.GetSection(x => x.SpeedRatio < speedRatio, out index); - var retVal = VectoMath.Interpolate(TorqueConverterEntries[index].SpeedRatio, - TorqueConverterEntries[index + 1].SpeedRatio, TorqueConverterEntries[index].TorqueRatio, - TorqueConverterEntries[index + 1].TorqueRatio, speedRatio); - return retVal; + return TorqueConverterEntries.Interpolate(x => x.SpeedRatio, y => y.TorqueRatio, speedRatio); } private NewtonMeter ReferenceTorqueLookup(double speedRatio) { - int index; - TorqueConverterEntries.GetSection(x => x.SpeedRatio < speedRatio, out index); - var retVal = VectoMath.Interpolate(TorqueConverterEntries[index].SpeedRatio, - TorqueConverterEntries[index + 1].SpeedRatio, TorqueConverterEntries[index].Torque, - TorqueConverterEntries[index + 1].Torque, speedRatio); - return retVal; + return TorqueConverterEntries.Interpolate(x => x.SpeedRatio, y => y.Torque, speedRatio); } // ReSharper disable once UnusedMember.Global -- used by validation diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Impl/ATGearbox.cs b/VectoCore/VectoCore/Models/SimulationComponent/Impl/ATGearbox.cs index e3a9e76932660547c4c7712d3fb64f544fe33611..60f27de92a3cd38d46cfa94ff5add5e5ec35ffab 100644 --- a/VectoCore/VectoCore/Models/SimulationComponent/Impl/ATGearbox.cs +++ b/VectoCore/VectoCore/Models/SimulationComponent/Impl/ATGearbox.cs @@ -46,28 +46,29 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl { public class ATGearbox : AbstractGearbox<ATGearbox.ATGearboxState> { - protected internal bool Disengaged = true; - - private readonly IShiftStrategy Strategy; - + private readonly IShiftStrategy _strategy; protected internal readonly TorqueConverter TorqueConverter; + private IIdleController _idleController; + // state overlapping property public Second LastShift { get; private set; } + public bool TorqueConverterLocked + { + get { return CurrentState.TorqueConverterLocked; } + set { CurrentState.TorqueConverterLocked = value; } + } + public ATGearbox(IVehicleContainer container, GearboxData gearboxModelData, IShiftStrategy strategy, KilogramSquareMeter engineInertia) : base(container, gearboxModelData) { - Strategy = strategy; - Strategy.Gearbox = this; + _strategy = strategy; + _strategy.Gearbox = this; LastShift = -double.MaxValue.SI<Second>(); - TorqueConverter = new TorqueConverter(this, Strategy, container, gearboxModelData.TorqueConverterData, engineInertia); + TorqueConverter = new TorqueConverter(this, _strategy, container, gearboxModelData.TorqueConverterData, engineInertia); } - private IIdleController _idleController; - - public bool TorqueConverterLocked { get; protected internal set; } - public IIdleController IdleController { get { return _idleController; } @@ -78,23 +79,34 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl } } + public bool Disengaged + { + get { return CurrentState.Disengaged; } + set { CurrentState.Disengaged = value; } + } + public override void Connect(ITnOutPort other) { base.Connect(other); TorqueConverter.NextComponent = other; } + public override bool ClutchClosed(Second absTime) + { + return true; + } + public override IResponse Initialize(NewtonMeter outTorque, PerSecond outAngularVelocity) { - if (Disengaged) { - Gear = Strategy.InitGear(0.SI<Second>(), Constants.SimulationSettings.TargetTimeInterval, outTorque, + if (CurrentState.Disengaged) { + Gear = _strategy.InitGear(0.SI<Second>(), Constants.SimulationSettings.TargetTimeInterval, outTorque, outAngularVelocity); } var inAngularVelocity = 0.SI<PerSecond>(); var inTorque = 0.SI<NewtonMeter>(); var effectiveRatio = ModelData.Gears[Gear].Ratio; var effectiveLossMap = ModelData.Gears[Gear].LossMap; - if (!TorqueConverterLocked) { + if (!CurrentState.TorqueConverterLocked) { effectiveRatio = ModelData.Gears[Gear].TorqueConverterRatio; effectiveLossMap = ModelData.Gears[Gear].TorqueConverterGearLossMap; } @@ -105,20 +117,20 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl inTorque = outTorque / effectiveRatio + torqueLossResult.Value; } - if (Disengaged) { + if (CurrentState.Disengaged) { return NextComponent.Initialize(0.SI<NewtonMeter>(), null); } - if (!TorqueConverterLocked && !ModelData.Gears[Gear].HasTorqueConverter) { + if (!CurrentState.TorqueConverterLocked && !ModelData.Gears[Gear].HasTorqueConverter) { throw new VectoSimulationException("Torque converter requested by strategy for gear without torque converter!"); } - var response = TorqueConverterLocked + var response = CurrentState.TorqueConverterLocked ? NextComponent.Initialize(inTorque, inAngularVelocity) : TorqueConverter.Initialize(inTorque, inAngularVelocity); PreviousState.SetState(inTorque, inAngularVelocity, outTorque, outAngularVelocity); PreviousState.Gear = Gear; - PreviousState.TorqueConverterLocked = TorqueConverterLocked; + PreviousState.TorqueConverterLocked = CurrentState.TorqueConverterLocked; return response; } @@ -150,7 +162,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl Case<ResponseOverload>(). Default(r => { throw new UnexpectedResponseException("AT-Gearbox.Initialize", r); }); - return new ResponseDryRun() { + return new ResponseDryRun { Source = this, EngineSpeed = response.EngineSpeed, EnginePowerRequest = response.EnginePowerRequest, @@ -165,29 +177,30 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl Log.Debug("AT-Gearbox Power Request: torque: {0}, angularVelocity: {1}", outTorque, outAngularVelocity); - if ((DataBus.VehicleStopped && outAngularVelocity > 0) || (Disengaged && outTorque.IsGreater(0))) { + if (!dryRun && + ((DataBus.VehicleStopped && outAngularVelocity > 0) || (CurrentState.Disengaged && outTorque.IsGreater(0)))) { Gear = 1; //Strategy.InitGear(absTime, dt, outTorque, outAngularVelocity); - TorqueConverterLocked = false; + CurrentState.TorqueConverterLocked = false; LastShift = absTime; - Disengaged = false; + CurrentState.Disengaged = false; } IResponse retVal; var count = 0; var loop = false; do { - if (Disengaged || (DataBus.DriverBehavior == DrivingBehavior.Halted)) { + if (CurrentState.Disengaged || (DataBus.DriverBehavior == DrivingBehavior.Halted)) { // only when vehicle is halted or close before halting retVal = RequestDisengaged(absTime, dt, outTorque, outAngularVelocity, dryRun); } else { - Disengaged = false; + CurrentState.Disengaged = false; retVal = RequestEngaged(absTime, dt, outTorque, outAngularVelocity, dryRun); IdleController.Reset(); } retVal.Switch() .Case<ResponseGearShift>(r => { loop = true; - Gear = Strategy.Engage(absTime, dt, outTorque, outAngularVelocity); + Gear = _strategy.Engage(absTime, dt, outTorque, outAngularVelocity); LastShift = absTime; }); } while (loop && ++count < 2); @@ -201,7 +214,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl { var effectiveRatio = ModelData.Gears[Gear].Ratio; var effectiveLossMap = ModelData.Gears[Gear].LossMap; - if (!TorqueConverterLocked) { + if (!CurrentState.TorqueConverterLocked) { effectiveRatio = ModelData.Gears[Gear].TorqueConverterRatio; effectiveLossMap = ModelData.Gears[Gear].TorqueConverterGearLossMap; } @@ -214,7 +227,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl var inTorque = outTorque / effectiveRatio + inTorqueLossResult.Value; - if (!TorqueConverterLocked && !ModelData.Gears[Gear].HasTorqueConverter) { + if (!CurrentState.TorqueConverterLocked && !ModelData.Gears[Gear].HasTorqueConverter) { throw new VectoSimulationException("Torque converter requested by strategy for gear without torque converter!"); } var inAngularVelocity = outAngularVelocity * effectiveRatio; @@ -227,14 +240,13 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl CurrentState.SetState(inTorque, inAngularVelocity, outTorque, outAngularVelocity); CurrentState.Gear = Gear; - CurrentState.TorqueConverterLocked = TorqueConverterLocked; CurrentState.TransmissionTorqueLoss = inTorque - outTorque / effectiveRatio; - if (!TorqueConverterLocked) { + if (!CurrentState.TorqueConverterLocked) { return TorqueConverter.Request(absTime, dt, inTorque, inAngularVelocity, dryRun); } if (!dryRun && - Strategy.ShiftRequired(absTime, dt, outTorque, outAngularVelocity, inTorque, inAngularVelocity, Gear, LastShift)) { + _strategy.ShiftRequired(absTime, dt, outTorque, outAngularVelocity, inTorque, inAngularVelocity, Gear, LastShift)) { return new ResponseGearShift() { Source = this }; @@ -291,9 +303,8 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl var avgInAngularSpeed = (PreviousState.InAngularVelocity + CurrentState.InAngularVelocity) / 2.0; - container[ModalResultField.Gear] = Disengaged || DataBus.VehicleStopped ? 0 : Gear; - container[ModalResultField.TC_Locked] = TorqueConverterLocked; - + container[ModalResultField.Gear] = CurrentState.Disengaged || DataBus.VehicleStopped ? 0 : Gear; + container[ModalResultField.TC_Locked] = CurrentState.TorqueConverterLocked; container[ModalResultField.P_gbx_loss] = CurrentState.TransmissionTorqueLoss * avgInAngularSpeed; container[ModalResultField.P_gbx_inertia] = CurrentState.InertiaTorqueLossOut * avgInAngularSpeed; container[ModalResultField.P_gbx_in] = CurrentState.InTorque * avgInAngularSpeed; @@ -301,40 +312,32 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl protected override void DoCommitSimulationStep() { - if (!Disengaged) { - if (CurrentState.TorqueLossResult != null && CurrentState.TorqueLossResult.Extrapolated) { - Log.Warn( - "Gear {0} LossMap data was extrapolated: range for loss map is not sufficient: n:{1}, torque:{2}, ratio:{3}", - Gear, CurrentState.OutAngularVelocity.ConvertTo().Rounds.Per.Minute, CurrentState.OutTorque, + if (!CurrentState.Disengaged && CurrentState.TorqueLossResult != null && CurrentState.TorqueLossResult.Extrapolated) { + Log.Warn( + "Gear {0} LossMap data was extrapolated: range for loss map is not sufficient: n:{1}, torque:{2}, ratio:{3}", + Gear, CurrentState.OutAngularVelocity.ConvertTo().Rounds.Per.Minute, CurrentState.OutTorque, + ModelData.Gears[Gear].Ratio); + if (DataBus.ExecutionMode == ExecutionMode.Declaration) { + throw new VectoException( + "Gear {0} LossMap data was extrapolated in Declaration Mode: range for loss map is not sufficient: n:{1}, torque:{2}, ratio:{3}", + Gear, CurrentState.InAngularVelocity.ConvertTo().Rounds.Per.Minute, CurrentState.InTorque, ModelData.Gears[Gear].Ratio); - if (DataBus.ExecutionMode == ExecutionMode.Declaration) { - throw new VectoException( - "Gear {0} LossMap data was extrapolated in Declaration Mode: range for loss map is not sufficient: n:{1}, torque:{2}, ratio:{3}", - Gear, CurrentState.InAngularVelocity.ConvertTo().Rounds.Per.Minute, CurrentState.InTorque, - ModelData.Gears[Gear].Ratio); - } } } if (DataBus.VehicleStopped) { - Disengaged = true; + CurrentState.Disengaged = true; } + AdvanceState(); - } - public override bool ClutchClosed(Second absTime) - { - return true; + CurrentState.TorqueConverterLocked = PreviousState.TorqueConverterLocked; + CurrentState.Disengaged = PreviousState.Disengaged; } public class ATGearboxState : GearboxState { public bool TorqueConverterLocked; - - //public PerSecond TorqueConverterTorqueOut; - //public PerSecond TorqueConverterAngularSpeedOut; - - //public double TorqueConverterSpeedRatio; - //public double TorqueConverterTorqueRatio; + public bool Disengaged = true; } } } \ No newline at end of file diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Impl/ATShiftStrategy.cs b/VectoCore/VectoCore/Models/SimulationComponent/Impl/ATShiftStrategy.cs index 30759237beb28c4a4a3ee4e8c73642d6b4582b37..7b087997dfe23728d1f4193c63fdaa18267cbfb1 100644 --- a/VectoCore/VectoCore/Models/SimulationComponent/Impl/ATShiftStrategy.cs +++ b/VectoCore/VectoCore/Models/SimulationComponent/Impl/ATShiftStrategy.cs @@ -112,9 +112,9 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl return false; } - // _ -> 1C: if n_eng == 0 + // L -> 0: disengage if inAngularVelocity == 0 if (_gearbox.TorqueConverterLocked && inAngularVelocity.IsEqual(0.SI<PerSecond>())) { - NextGear.SetState(absTime, false, 1, false); + NextGear.SetState(absTime, true, 1, false); return true; } diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Impl/CombustionEngine.cs b/VectoCore/VectoCore/Models/SimulationComponent/Impl/CombustionEngine.cs index 6c76f1b80a5a91d500ccb4f5edc2d03827c5d5c7..6130063dfb4d8bcf4fa42e4e8d1c981434fcb1ec 100644 --- a/VectoCore/VectoCore/Models/SimulationComponent/Impl/CombustionEngine.cs +++ b/VectoCore/VectoCore/Models/SimulationComponent/Impl/CombustionEngine.cs @@ -248,7 +248,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl maxTorque = VectoMath.Min(maxTorque, gearboxFullLoad); } - CurrentState.EngineTorque = totalTorqueDemand.Limit(minTorque, maxTorque); + CurrentState.EngineTorque = totalTorqueDemand.LimitTo(minTorque, maxTorque); CurrentState.EnginePower = CurrentState.EngineTorque * avgEngineSpeed; if (totalTorqueDemand.IsGreater(0) && diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Impl/CycleGearbox.cs b/VectoCore/VectoCore/Models/SimulationComponent/Impl/CycleGearbox.cs index 549e8b1c9d5bf85507401d4500e63c45416d4c47..a6ec19a0b78bbc3d3d8d622f723f7ad0b9730774 100644 --- a/VectoCore/VectoCore/Models/SimulationComponent/Impl/CycleGearbox.cs +++ b/VectoCore/VectoCore/Models/SimulationComponent/Impl/CycleGearbox.cs @@ -364,18 +364,18 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl private TorqueConverterOperatingPoint FindOperatingPoint(NewtonMeter outTorque, PerSecond outAngularVelocity) { - try { - var operatingPointList = TorqueConverter.FindOperatingPoint(outTorque, outAngularVelocity, DataBus.EngineIdleSpeed); - var operatingPoint = SelectOperatingPoint(operatingPointList); - if (operatingPoint.InAngularVelocity.IsGreater(DataBus.EngineRatedSpeed)) { - operatingPoint = TorqueConverter.FindOperatingPoint(DataBus.EngineRatedSpeed, outAngularVelocity); - } - return operatingPoint; - } catch (VectoException ve) { - Log.Debug(ve, "failed to find torque converter operating point, fallback: creeping"); + var operatingPointList = TorqueConverter.FindOperatingPoint(outTorque, outAngularVelocity, DataBus.EngineIdleSpeed); + if (operatingPointList.Count == 0) { + Log.Debug("CycleGearbox: Failed to find torque converter operating point, fallback: creeping"); var tqOperatingPoint = TorqueConverter.FindOperatingPoint(DataBus.EngineIdleSpeed, outAngularVelocity); return tqOperatingPoint; } + + var operatingPoint = SelectOperatingPoint(operatingPointList); + if (operatingPoint.InAngularVelocity.IsGreater(DataBus.EngineRatedSpeed)) { + operatingPoint = TorqueConverter.FindOperatingPoint(DataBus.EngineRatedSpeed, outAngularVelocity); + } + return operatingPoint; } private TorqueConverterOperatingPoint SelectOperatingPoint(IList<TorqueConverterOperatingPoint> operatingPointList) diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Impl/TorqueConverter.cs b/VectoCore/VectoCore/Models/SimulationComponent/Impl/TorqueConverter.cs index a5a6ed33a8e4b536a4c41da742f1c3622df033f8..89c0ff871423a32e977941bfb2ad2ef9f7f6bd5b 100644 --- a/VectoCore/VectoCore/Models/SimulationComponent/Impl/TorqueConverter.cs +++ b/VectoCore/VectoCore/Models/SimulationComponent/Impl/TorqueConverter.cs @@ -82,21 +82,13 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl return retVal; } - public IResponse Request(Second absTime, Second dt, NewtonMeter outTorque, PerSecond outAngularVelocity, bool dryRun = false) { if (dryRun) { var dryOperatingPoint = FindOperatingPoint(outTorque, outAngularVelocity); - var engineResponse = - (ResponseDryRun)NextComponent.Request(absTime, dt, dryOperatingPoint.InTorque, dryOperatingPoint.InAngularVelocity, - true); - - var deltaTorqueConverter = (outTorque - dryOperatingPoint.OutTorque) * - (PreviousState.OutAngularVelocity + dryOperatingPoint.OutAngularVelocity) / 2.0; - - var deltaEngine = (engineResponse.DeltaFullLoad > 0 ? engineResponse.DeltaFullLoad : 0.SI<Watt>()) + - (engineResponse.DeltaDragLoad < 0 ? -engineResponse.DeltaDragLoad : 0.SI<Watt>()); + var engineResponse = (ResponseDryRun) + NextComponent.Request(absTime, dt, dryOperatingPoint.InTorque, dryOperatingPoint.InAngularVelocity, true); dryOperatingPoint = outTorque.IsGreater(0) && DataBus.BrakePower.IsEqual(0) ? GetMaxPowerOperatingPoint(dt, outAngularVelocity, engineResponse) @@ -104,10 +96,9 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl engineResponse = (ResponseDryRun)NextComponent.Request(absTime, dt, dryOperatingPoint.InTorque, dryOperatingPoint.InAngularVelocity, true); - var delta = (outTorque - dryOperatingPoint.OutTorque) * (PreviousState.OutAngularVelocity + dryOperatingPoint.OutAngularVelocity) / 2.0; - //deltaTorqueConverter.Value() * (deltaEngine.IsEqual(0) ? 1 : deltaEngine.Value()); + return new ResponseDryRun() { Source = this, DeltaFullLoad = delta, @@ -182,39 +173,41 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl protected internal TorqueConverterOperatingPoint FindOperatingPoint(NewtonMeter outTorque, PerSecond outAngularVelocity) { - try { - var operatingPointList = ModelData.FindOperatingPoint(outTorque, outAngularVelocity, DataBus.EngineIdleSpeed); - var operatingPoint = SelectOperatingPoint(operatingPointList); - if (operatingPoint.InAngularVelocity.IsSmaller(DataBus.EngineIdleSpeed)) { - throw new VectoException("Invalid operating point, inAngularVelocity below engine's idle speed: {0}", - operatingPoint.InAngularVelocity); - } - if (operatingPoint.InAngularVelocity.IsGreater(DataBus.EngineRatedSpeed)) { - operatingPoint = ModelData.FindOperatingPoint(DataBus.EngineRatedSpeed, outAngularVelocity); - } - return operatingPoint; - } catch (VectoException ve) { - Log.Debug(ve, "failed to find torque converter operating point, fallback: creeping"); + var operatingPointList = ModelData.FindOperatingPoint(outTorque, outAngularVelocity, DataBus.EngineIdleSpeed); + if (operatingPointList.Count == 0) { + Log.Debug("TorqueConverter: Failed to find torque converter operating point, fallback: creeping"); var tqOperatingPoint = ModelData.FindOperatingPoint(DataBus.EngineIdleSpeed, outAngularVelocity); return tqOperatingPoint; } - } + var operatingPoint = SelectOperatingPoint(operatingPointList); + if (operatingPoint.InAngularVelocity.IsSmaller(DataBus.EngineIdleSpeed)) { + throw new VectoException("Invalid operating point, inAngularVelocity below engine's idle speed: {0}", + operatingPoint.InAngularVelocity); + } + if (operatingPoint.InAngularVelocity.IsGreater(DataBus.EngineRatedSpeed)) { + operatingPoint = ModelData.FindOperatingPoint(DataBus.EngineRatedSpeed, outAngularVelocity); + } + return operatingPoint; + } private TorqueConverterOperatingPoint SelectOperatingPoint(IList<TorqueConverterOperatingPoint> operatingPointList) { if (operatingPointList.Count == 1) { return operatingPointList[0]; } + var filtered = operatingPointList.Where(x => - (x.InTorque * x.InAngularVelocity).IsSmallerOrEqual(DataBus.EngineStationaryFullPower(x.InAngularVelocity), - Constants.SimulationSettings.LineSearchTolerance.SI<Watt>()) && - (x.InTorque * x.InAngularVelocity).IsGreaterOrEqual(DataBus.EngineDragPower(x.InAngularVelocity), - Constants.SimulationSettings.LineSearchTolerance.SI<Watt>()) - ).ToArray(); - if (filtered.Count() == 1) { + (x.InTorque * x.InAngularVelocity).IsSmallerOrEqual(DataBus.EngineStationaryFullPower(x.InAngularVelocity), + Constants.SimulationSettings.LineSearchTolerance.SI<Watt>()) && + (x.InTorque * x.InAngularVelocity).IsGreaterOrEqual(DataBus.EngineDragPower(x.InAngularVelocity), + Constants.SimulationSettings.LineSearchTolerance.SI<Watt>()) + ).ToList(); + + if (filtered.Count == 1) { return filtered.First(); } + return operatingPointList[0]; } diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Impl/Vehicle.cs b/VectoCore/VectoCore/Models/SimulationComponent/Impl/Vehicle.cs index 1a6f138c55412228ee3d74212d32774784eaf6df..f5abf10e10be1be0698e6672eeef4f97ed0438d4 100644 --- a/VectoCore/VectoCore/Models/SimulationComponent/Impl/Vehicle.cs +++ b/VectoCore/VectoCore/Models/SimulationComponent/Impl/Vehicle.cs @@ -94,7 +94,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl CurrentState.SimulationInterval = dt; CurrentState.Acceleration = acceleration; CurrentState.Velocity = PreviousState.Velocity + acceleration * dt; - if (CurrentState.Velocity.IsSmallerOrEqual(0.SI<MeterPerSecond>(), + if (CurrentState.Velocity.IsEqual(0.SI<MeterPerSecond>(), Constants.SimulationSettings.VehicleSpeedHaltTolerance)) { CurrentState.Velocity = 0.SI<MeterPerSecond>(); } diff --git a/VectoCore/VectoCore/VectoCore.csproj b/VectoCore/VectoCore/VectoCore.csproj index 8c796599514490b71e05f9c2dd89f5537a9eaa5d..e7064635d155344dcb6ce8c27ed82f60597f5072 100644 --- a/VectoCore/VectoCore/VectoCore.csproj +++ b/VectoCore/VectoCore/VectoCore.csproj @@ -109,6 +109,7 @@ </ItemGroup> <ItemGroup> <Compile Include="Configuration\Constants.cs" /> + <Compile Include="InputData\AuxiliaryFileHelper.cs" /> <Compile Include="InputData\FileIO\JSON\JSONComponentInputData.cs" /> <Compile Include="InputData\FileIO\JSON\JsonExtensionMethods.cs" /> <Compile Include="InputData\Impl\InputData.cs" /> diff --git a/VectoCore/VectoCoreTest/Models/Simulation/AuxTests.cs b/VectoCore/VectoCoreTest/Models/Simulation/AuxTests.cs index 9f87714bc7943e9d4b9767c46cc078b5f2f44f4e..0a31e3c5ba9068427b31f757c2b913dfd469e4d8 100644 --- a/VectoCore/VectoCoreTest/Models/Simulation/AuxTests.cs +++ b/VectoCore/VectoCoreTest/Models/Simulation/AuxTests.cs @@ -29,11 +29,15 @@ * Martin Rexeis, rexeis@ivt.tugraz.at, IVT, Graz University of Technology */ +using System.Collections.Generic; using Microsoft.VisualStudio.TestTools.UnitTesting; using TUGraz.VectoCommon.Exceptions; +using TUGraz.VectoCommon.InputData; using TUGraz.VectoCommon.Models; using TUGraz.VectoCommon.Utils; +using TUGraz.VectoCore.InputData; using TUGraz.VectoCore.InputData.FileIO.JSON; +using TUGraz.VectoCore.InputData.Impl; using TUGraz.VectoCore.InputData.Reader; using TUGraz.VectoCore.InputData.Reader.ComponentData; using TUGraz.VectoCore.Models.Declaration; @@ -193,7 +197,14 @@ namespace TUGraz.VectoCore.Tests.Models.Simulation var aux = new EngineAuxiliary(container); - var auxData = AuxiliaryDataReader.ReadFromFile(@"TestData\Components\24t_Coach_ALT.vaux", "ALT"); + var auxDataInputData = new AuxiliaryDataInputData { + ID = "ALT1", + Type = AuxiliaryType.ElectricSystem, + Technology = new List<string>(), + }; + AuxiliaryFileHelper.FillAuxiliaryDataInputData(auxDataInputData, @"TestData\Components\24t_Coach_ALT.vaux"); + var auxData = AuxiliaryDataReader.Create(auxDataInputData); + // ratio = 4.078 // efficiency_engine = 0.96 // efficiency_supply = 0.98 @@ -252,7 +263,14 @@ namespace TUGraz.VectoCore.Tests.Models.Simulation var aux = new EngineAuxiliary(container); - var auxData = AuxiliaryDataReader.ReadFromFile(@"TestData\Components\24t_Coach_ALT.vaux", "ALT"); + var auxDataInputData = new AuxiliaryDataInputData { + ID = "ALT1", + Type = AuxiliaryType.ElectricSystem, + Technology = new List<string>(), + }; + AuxiliaryFileHelper.FillAuxiliaryDataInputData(auxDataInputData, @"TestData\Components\24t_Coach_ALT.vaux"); + var auxData = AuxiliaryDataReader.Create(auxDataInputData); + // ratio = 4.078 // efficiency_engine = 0.96 // efficiency_supply = 0.98 @@ -303,8 +321,10 @@ namespace TUGraz.VectoCore.Tests.Models.Simulation [TestMethod] public void AuxFileMissing() { - AssertHelper.Exception<VectoException>(() => AuxiliaryDataReader.ReadFromFile(@"NOT_EXISTING_AUX_FILE.vaux", "N.A."), - "Auxiliary file not found: NOT_EXISTING_AUX_FILE.vaux"); + AssertHelper.Exception<VectoException>(() => { + var auxDataInputData = new AuxiliaryDataInputData(); + AuxiliaryFileHelper.FillAuxiliaryDataInputData(auxDataInputData, @"NOT_EXISTING_AUX_FILE.vaux"); + }, "Auxiliary file not found: NOT_EXISTING_AUX_FILE.vaux"); } [TestMethod] diff --git a/VectoCore/VectoCoreTest/Utils/VectoMathTest.cs b/VectoCore/VectoCoreTest/Utils/VectoMathTest.cs index 406737b20d19972289da036b0477172d1eff8084..b38f0dce86ee39b2a126a392aa8294a6ea384a03 100644 --- a/VectoCore/VectoCoreTest/Utils/VectoMathTest.cs +++ b/VectoCore/VectoCoreTest/Utils/VectoMathTest.cs @@ -58,7 +58,6 @@ namespace TUGraz.VectoCore.Tests.Utils Assert.AreEqual(positive, VectoMath.Abs(negative)); Assert.AreEqual(positive, VectoMath.Abs(positive)); - var smallerWatt = 0.SI<Watt>(); var biggerWatt = 5.SI<Watt>(); var negativeWatt = -10.SI<Watt>(); @@ -68,12 +67,10 @@ namespace TUGraz.VectoCore.Tests.Utils Assert.AreEqual(biggerWatt, VectoMath.Max(smallerWatt, biggerWatt)); - Assert.AreEqual(positiveWatt, VectoMath.Abs(negativeWatt)); Assert.AreEqual(positiveWatt, VectoMath.Abs(positiveWatt)); } - [TestCase(0, -1, 0, 1, -1, 0, 1, 0, 0, 0), TestCase(0, 0, 10, 0, 0, 5, 10, 5, double.NaN, double.NaN), TestCase(0, 0, 0, 10, 5, 0, 10, 5, double.NaN, double.NaN), @@ -101,10 +98,10 @@ namespace TUGraz.VectoCore.Tests.Utils { var results = VectoMath.CubicEquationSolver(a, b, c, d); - Assert.AreEqual(expected.Length, results.Count); + Assert.AreEqual(expected.Length, results.Length); var sorted = expected.ToList(); sorted.Sort(); - results.Sort(); + Array.Sort(results); var comparison = sorted.Zip(results, (exp, result) => exp - result); foreach (var cmp in comparison) {