Skip to content

Commit 42e81b1

Browse files
authored
Tolerance to avoid potential precision issues (#288)
Equality comparison of floating point numbers. Possible loss of precision while rounding values.
1 parent b499fe3 commit 42e81b1

File tree

5 files changed

+25
-17
lines changed

5 files changed

+25
-17
lines changed

BardMusicPlayer.Script/BasicSharp/Interpreter.cs

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
using System;
12
using System.Collections.Generic;
23
using System.Globalization;
34
using System.Threading.Tasks;
@@ -286,8 +287,9 @@ private void Goto()
286287

287288
private void If()
288289
{
290+
const float tolerance = 0.0001f; // define a small tolerance value
289291
// check if argument is equal to 0
290-
var result = Expr().BinOp(new Value(0), Token.Equal).Real == 1;
292+
var result = Math.Abs(Expr().BinOp(new Value(0), Token.Equal).Real - 1) < tolerance;
291293

292294
Match(Token.Then);
293295
GetNextToken();
@@ -411,8 +413,9 @@ private void For()
411413
loopsteps.Add(var, step);
412414
}
413415
}
414-
415-
if (vars[var].BinOp(v, Token.More).Real == 1)
416+
417+
const float tolerance = 0.0001f; // define a small tolerance value
418+
if (Math.Abs(vars[var].BinOp(v, Token.More).Real - 1) < tolerance)
416419
{
417420
while (true)
418421
{
@@ -447,7 +450,8 @@ private void Next()
447450

448451
private void Assert()
449452
{
450-
var result = Expr().BinOp(new Value(0), Token.Equal).Real == 1;
453+
const float tolerance = 0.0001f; // define a small tolerance value
454+
var result = Math.Abs(Expr().BinOp(new Value(0), Token.Equal).Real - 1) < tolerance;
451455

452456
if (result)
453457
{

BardMusicPlayer.Script/BasicSharp/Value.cs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,7 @@ public readonly Value UnaryOp(Token tok)
6868
public readonly Value BinOp(Value b, Token tok)
6969
{
7070
var a = this;
71+
const float tolerance = 0.0001f; // define a small tolerance value
7172
if (a.Type != b.Type)
7273
{
7374
// promote one value to higher type
@@ -82,9 +83,9 @@ public readonly Value BinOp(Value b, Token tok)
8283
case Token.Plus:
8384
return a.Type == ValueType.Real ? new Value(a.Real + b.Real) : new Value(a.String + b.String);
8485
case Token.Equal:
85-
return a.Type == ValueType.Real ? new Value(a.Real == b.Real ? 1 : 0) : new Value(a.String == b.String ? 1 : 0);
86+
return a.Type == ValueType.Real ? new Value(Math.Abs(a.Real - b.Real) < tolerance ? 1 : 0) : new Value(a.String == b.String ? 1 : 0);
8687
case Token.NotEqual:
87-
return a.Type == ValueType.Real ? new Value(a.Real == b.Real ? 0 : 1) : new Value(a.String == b.String ? 0 : 1);
88+
return a.Type == ValueType.Real ? new Value(Math.Abs(a.Real - b.Real) < tolerance ? 0 : 1) : new Value(a.String == b.String ? 0 : 1);
8889
default:
8990
{
9091
if (a.Type == ValueType.String)

BardMusicPlayer.Transmogrify/Song/Importers/GuitarPro/GP6File.cs

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,8 @@ public sealed class GP6File : GPFile
2222
public static int totalLength;
2323
public static int lengthPassed;
2424

25-
private readonly byte[] udata; //uncompressed data
26-
25+
private readonly byte[] udata; //uncompressed data
26+
const float tolerance = 0.0001f; // define a small tolerance value
2727
//public List<Track> tracks;
2828
public GP6File(byte[] _data)
2929
{
@@ -441,15 +441,15 @@ public static Beat transferBeat(Node node, int index, Voice voice)
441441

442442
if (hasWhammy)
443443
{
444-
if (whammyBarMiddleOffset1 == -1.0f)
444+
if (Math.Abs(whammyBarMiddleOffset1 - (-1.0f)) < tolerance)
445445
{
446446
whammyBarMiddleOffset1 = whammyBarOriginOffset +
447447
(whammyBarDestinationOffset - whammyBarOriginOffset) / 2.0f;
448448
whammyBarMiddleValue =
449449
whammyBarOriginValue + (whammyBarDestinationValue - whammyBarOriginValue) / 2.0f;
450450
}
451451

452-
if (whammyBarMiddleOffset2 == -1.0f) whammyBarMiddleOffset2 = whammyBarMiddleOffset1;
452+
if (Math.Abs(whammyBarMiddleOffset2 - (-1.0f)) < tolerance) whammyBarMiddleOffset2 = whammyBarMiddleOffset1;
453453
beat.effect.tremoloBar = new BendEffect
454454
{
455455
type = BendType.none, //Not defined in GP6
@@ -674,13 +674,13 @@ public static Note transferNote(Node node, int index, Beat beat, int velocity, G
674674

675675
if (hasBendEffect)
676676
{
677-
if (bendMidOff1 == -1.0f)
677+
if (Math.Abs(bendMidOff1 - (-1.0f)) < tolerance)
678678
{
679679
bendMidOff1 = bendOrigOff + (bendDestOff - bendOrigOff) / 2.0f;
680680
bendMidVal = bendOrigVal + (bendDestVal - bendOrigVal) / 2.0f;
681681
}
682682

683-
if (bendMidOff2 == -1.0f) bendMidOff2 = bendMidOff1;
683+
if (Math.Abs(bendMidOff2 - (-1.0f)) < tolerance) bendMidOff2 = bendMidOff1;
684684

685685
bendEffect.points.Add(new BendPoint(0.0f, bendOrigVal));
686686
bendEffect.points.Add(new BendPoint(bendOrigOff, bendOrigVal));
@@ -697,7 +697,7 @@ public static Note transferNote(Node node, int index, Beat beat, int velocity, G
697697
note.effect.bend = bendEffect;
698698
}
699699

700-
if (harmonicFret != -1)
700+
if (Math.Abs(harmonicFret - (-1)) > tolerance)
701701
{
702702
switch (harmonicType)
703703
{

BardMusicPlayer.Transmogrify/Song/Importers/GuitarPro/Native/NativeFormat.cs

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -398,8 +398,9 @@ public List<Note> retrieveNotes(GuitarPro.Track track, int[] tuning, Track myTra
398398

399399
if (last != null)
400400
{
401-
note.fret = last.fret; //For GP3 & GP4
402-
if (last.harmonic != note.harmonic || last.harmonicFret != note.harmonicFret
401+
note.fret = last.fret; //For GP3 & GP4
402+
const float tolerance = 0.0001f; // define a small tolerance value
403+
if (last.harmonic != note.harmonic || Math.Abs(last.harmonicFret - note.harmonicFret) > tolerance
403404
)
404405
dontAddNote = false;
405406

@@ -759,7 +760,8 @@ public static List<Tempo> retrieveTempos(GPFile file)
759760
position = pos
760761
};
761762
pos += flipDuration(mh.timeSignature.denominator) * mh.timeSignature.numerator;
762-
if (oldTempo != t.value) tempos.Add(t);
763+
const float tolerance = 0.0001f; // define a small tolerance value
764+
if (Math.Abs(oldTempo - t.value) > tolerance) tempos.Add(t);
763765
oldTempo = t.value;
764766
}
765767
}

BardMusicPlayer/UI_Classic/Classic_Siren.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -183,7 +183,8 @@ private void Siren_PlaybackTimeChanged(double currentTime, double endTime, int a
183183
Siren_VoiceCount.Content = activeVoices.ToString();
184184

185185
TimeSpan t;
186-
if (Siren_Position.Maximum != endTime)
186+
const float tolerance = 0.0001f; // define a small tolerance value
187+
if (Math.Abs(Siren_Position.Maximum - endTime) > tolerance) // use tolerance to compare values
187188
{
188189
Siren_Position.Maximum = endTime;
189190
t = TimeSpan.FromMilliseconds(endTime);

0 commit comments

Comments
 (0)