Cuberite Forum
Normalize Zero Vector? - Printable Version

+- Cuberite Forum (https://forum.cuberite.org)
+-- Forum: Cuberite (https://forum.cuberite.org/forum-4.html)
+--- Forum: Development (https://forum.cuberite.org/forum-13.html)
+--- Thread: Normalize Zero Vector? (/thread-2059.html)



Normalize Zero Vector? - DiamondToaster - 07-17-2015

So, I've noticed that for a while, normalizing a zero-distance vector returns a nil value. Should this be fixed to return a zero vector? According to people on Stack Overflow, the normalized form of a zero vector is also a zero vector This would be useful so I don't have to check for nil values and use hackish workarounds.

http://stackoverflow.com/questions/722073/how-do-you-normalize-a-zero-vector


RE: Normalize Zero Vector? - NiLSPACE - 07-17-2015

When calling the Normalize function you normalize the vector you're calling the function on.. if that makes sense Wink


RE: Normalize Zero Vector? - DiamondToaster - 07-18-2015

I know that, but as the documentation for the Vector3d class says: Changes this vector so that it keeps current direction but is exactly 1 unit long. FIXME: Fails for a zero vector. If you set the coordinates for a vector, let's say, Direction. If you set each of Direction's coordinates to 0 then call Direction:Normalize(), the distance and each component become NaN when they should stay at 0.


RE: Normalize Zero Vector? - NiLSPACE - 07-18-2015

Oh, it shouldn't be too hard to do that right?
x = (x == 0) ? 0 : (1 / x);
y = (y == 0) ? 0 : (1 / y);
z = (z == 0) ? 0 : (1 / z);

This code doesn't work.


RE: Normalize Zero Vector? - DiamondToaster - 07-19-2015

I just feel that it should be handled by the server since it's a core function of a 3D vector. The API also says it's a "FIXME:." I'll probably look into making a patch or something, it should be really easy.


RE: Normalize Zero Vector? - NiLSPACE - 07-19-2015

Simply changing this line to something like:
double Len = 1.0 / (Length() == 0) ? 0.0000000001 : Length();
should work right?


RE: Normalize Zero Vector? - xoft - 07-19-2015

I think you should guide the optimizer to remove the double call to Length(), by storing it in a temporary variable.


RE: Normalize Zero Vector? - DiamondToaster - 07-20-2015

Maybe something like this?
I'm not sure how much of a performance impact an if statement and 3 divides will make.

	inline void Normalize(void)
	{
		double Len = Length();

		// If the length is zero, the vector cannot possibly have a direction.
		if (Len == 0.0d)
		{
			x = static_case<T>(0);
			y = static_case<T>(0);
			z = static_case<T>(0);
			return;
		}

		x = static_cast<T>(x / Len);
		y = static_cast<T>(y / Len);
		z = static_cast<T>(z / Len);
	}

I guess this also applies to Vector3::NormalizeCopy().


RE: Normalize Zero Vector? - xoft - 07-20-2015

(updated your post to use the correct code tag)

Basically, yes, but you don't want to compare to zero exactly, you want to compare to an epsilon (abs(Len) < EPS) to accommodate for numerical inaccuracy.