# Class with methods that depend on a variable argument, but this variable is constant throughout large parts of the application

I am looking for advice on how to design the following scenario:

I have a 3-dimensional vector class, the entries are of type `double`. I want two vectors to be considered equal if their corresponding elements differ by less than a given tolerance, e.g. 10^(-10).

(Code examples are in C# syntax mixed with pseudocode.)

``````public class Vector
{
double x, y, z;

public bool TolEquals(Vector other)
{
return ((|x-other.x| < 10^(-10))  // absolute value of difference
&& (|y-other.y| < 10^(-10))  // must be small enough
&& (|z-other.z| < 10^(-10)));
}
}
``````

I need a certain flexibility because other people might want to use another tolerance value than 10^(-10).

That means, I need to somehow incorporate the tolerance value into my equality checking method, e.g. so:

``````public bool TolEquals(Vector other, double tolerance)
{
return ((|x-other.x| < tolerance)
&& (|y-other.y| < tolerance)
&& (|z-other.z| < tolerance);
}
``````

But I know that throughout my application, the tolerance will be constant. And I do not want to write

``````v1.TolEquals(v2, tolerance)
``````

every time I check for equality since it is not very readable and since typos can happen easily.

Another idea is to store `tolerance` as a member of the `Vector` class and set it in the constructor of `Vector`. Then the `TolEquals` method needs only one argument:

``````public class Vector
{
double x, y, z;
double tolerance;

public Vector(double x, double y, double z, double tolerance)
{
this.x = x;
this.y = y;
this.z = z;
this.tolerance = tolerance;
}

public bool TolEquals(Vector other)
{
return ((|x-other.x| < tolerance)
&& (|y-other.y| < tolerance)
&& (|z-other.z| < tolerance));
}
}
``````

But then someone using my code could accidentally create two vectors `v` and `w` with different tolerances and would get different answers from `v.TolEquals(w)` and `w.TolEquals(v)`. That's not supposed to happen either.

I will probably add some static methods to my `Vector` class sooner or later that take several vectors as input and do some calculation involving `TolEquals` with them. So I need to make sure that all vectors use the same tolerance value.

I am looking for a solution that allows me to define `tolerance` somewhere in the program, outside the `Vector` class, and then all vectors use that `tolerance` for their `TolEquals`. And I want to be able to change `tolerance` at run-time (don't need it now but might need it later), resulting in all vectors using the new value instead. BUT it might be that someone using my code needs two different tolerance values coexisting. He would have two distinct groups of vectors, using the different tolerance values, but the groups do not interact with each other.

So a static field `tolerance` is no option either.

I will also write a `matrix` class and maybe some others that will have an analogue of `TolEquals`, so the solution should not be limited to my `Vector` class.

Any ideas?

EDIT:

Inspired by the accepted answer I feel like presenting my final solution (in C#) and put in some comments. All information is given in the accepted answer, but it took me some time to process it so I'll refine it a bit here. I decided to implement it with a static field for the tolerance in the generic vector class:

``````public interface ISpace { double TOL(); }

public class ZeroTolSpace : ISpace { public double TOL() => 0; }
public class Tol10Space : ISpace { public double TOL() => 1E-10; }
// Others can easily write new classes for other tolerance values.

public class Vector<T> where T: ISpace, new()
{
private double x, y, z;
public static double? tol = null; // Changeable at runtime (if really needed)!

public Vector(double x, double y, double z)
{
this.x = x; this.y = y; this.z = z;
tol = tol ?? (new T()).TOL(); // Since tol is static, the new-operator
// gets called only once, minimzing overhead.
}

public bool TolEquals(Vector other)
{
return ((Math.Abs(x-other.x) < tol)
&& (Math.Abs(y-other.y) < tol)
&& (Math.Abs(z-other.z) < tol));
}

}
``````

Then in the `Main` method we can do:

``````        Vector<ZeroTolSpace> v1 = new Vector<ZeroTolSpace> (0, 0, 0);
Vector<ZeroTolSpace> v2 = new Vector<ZeroTolSpace>(1E-11, 1E-11, 1E-11);
v1.TolEquals(v2)); // false since _tol is 0

Vector<Tol10Space> w1 = new Vector<Tol10Space> (0, 0, 0);
Vector<Tol10Space> w2 = new Vector<Tol10Space> (1E-11, 1E-11, 1E-11);
w1.TolEquals(w2)); // true since tol is 1E-10

v1.TolEquals(w2)); // compile error: types do not match
``````

Matrix and other classes depending on tolerance can be implemented in the same way.

• You're basically describing a configuration value. In C# this is usually accomplished with AppSettings. Jul 19, 2016 at 14:22
• So I need to make sure that all vectors use the same tolerance value. In that case `ToEquals` should check that both vectors have the same tolerance. Jul 19, 2016 at 15:00
• kind of irrelevant, but since you said you were writing C#: `10^(-10)` uses the bitwise XOR operator (`^`) and is equal to `-4`. what you want is `1e-10`.
– sara
Jul 19, 2016 at 16:34

But I know that throughout my application, the tolerance will be constant.

This is a bit suspect because such tolerance is usually very algorithm specific. I've had to deal with much pain because someone thought that it they could get away with using a constant tolerance everywhere.

But assuming, that you really do want this, I might do:

``````public class Space {
public Space(double tolerance);

public Vector vector(double x, double y, double z);
public Matrix matrix(...);
}
``````

So you create a `Space` class which provides the only way to create a vector. You can't combine vectors created by different space classes. Within a particular application, you simply create a Space constant which defines the tolerance you are using.

And I want to be able to change tolerance at run-time (don't need it now but might need it later), resulting in all vectors using the new value instead.

No, you don't. Changing the tolerance at runtime will lead to pain and suffering. If your code needs to have different tolerances in different circumstances, you really do want to pass a parameter around.

Now, really, what would be nice is if we could use generics:

``````Vector<MySpace>
``````

Then have a static method on MySpace define the tolerance. Then the type system could verify that you never mix different types of vectors. Alas, this is beyond some programming languages so you may or may not be able to use it.

== EDIT ==

C++ can do this very nicely with templates:

``````struct MySpace {
public static double tolerance = 0.000001;
}

template<typename T>
class Vector {
Vector(double x, double y, double z);

// We can refer to T::tolerance
}

// I can use Vector<MySpace> to refer to vectors with a particular
// space, and have the type system enforce that.
``````

But this depends on the fact that a C++ template can freely refer to elements inside its type parameters. But other languages often lack this.

In C# you could do something like (I don't do C#, but I believe this is valid)

``````interface Space {
double tolerance();
}

public class MySpace extends Space {
double tolerance() {
return 0.000001;
}
}

public class Vector<T> where T: Space, new() {
public Vector(double x, double y, double z);

// I can get my tolerance via (new T()).tolerance()
// We hope that the optimizer can get rid of the overhead.
}
``````

But in Java, that won't work, because we can't do `new T`. We could do something like:

``````class Vector<T extends Space> {
Vector(T t, double x, double y, double z);

// t.tolerance() will be the tolerance.
}
``````

And then follow a convention to always create instances of Space by a singleton subclass.

===

More detail on Java Solution

In library:

``````public interface Space {
double tolerance();

public static <T extends Space> double toleranceForSpace(Class<T> spaceClass) {
return spaceClass.newInstance().tolerance();
}
}

public Vector<SpaceType> {
Vector(Class<SpaceType> spaceType, double x, double y, double z);

// call Space.toleranceFor(spaceType) to get the tolerance
}
``````

In non-library code:

``````class MySpace extends Space {
double tolerance() { return 0.1; }
}

Vector<MySpace> space = new Vector<>(MySpace.class, 2.3, 4.5, 6.7);
``````
• @Kjara make `Vector` a non-static inner class and `classof(space1.Vector) != classof(space2.Vector)`, assuming that C# behaves like Java in that way Jul 19, 2016 at 17:56
• @Daenyth And how do I make `classof(space1.Vector) != classof(space2.Vector)`? If I define `Vector` as an inner class of `Space`, it is still possible to use `TolEquals` for vectors of different spaces... (C#) Jul 19, 2016 at 18:23
• @Kjara, I was thinking you would add a runtime check. But I've edited the answer with examples of possible solutions and half-solutions in a few different languages. Jul 19, 2016 at 19:38
• @Kjara it would be a type error, I would think. Or perhaps I've been in scala land too long. Jul 19, 2016 at 19:45
• @Kjara, the user of your code can easily define a new subclass and use that. Jul 20, 2016 at 14:17

Optional parameters can work nicely here.

``````public class Vector {
public static readonly double DefaultTolerance = 0.0001; // or whatever.

public bool Equals(Vector other, double? tolerance = null) {
tolerance = tolerance ?? DefaultTolerance;
• Do you think there is a significant performance difference between your version with optional argument and the (IMO cleaner) version of writing two different methods, `Equals(Vector other)` and `Equals(Vector other, double tolerance)` ? Jul 20, 2016 at 10:34