Torch rounding error on long cast

Hey everyone, i was doing some preprocessing on my data and realized that converting an array to a long torch tensor was consuming one of my classes. I’m pretty confused as to why this is happening. To give some context, my masks were created via VTK in C++ from cardiac contours.
Anyone might have any idea why this is happening?

>>> q = nib.load(os.path.join(trainseg_dir, os.listdir(trainseg_dir)[0])).get_fdata()
>>> print(np.unique(q))
[0.         1.00001526 2.        ]
>>> print(np.unique(torch.tensor(q).long()))
[0 1]
>>> print(np.unique(torch.tensor(np.round(q), dtype=torch.long)))
[0. 1. 2.]
>>> print(torch.nn.functional.one_hot(torch.tensor(q).long()).shape)
torch.Size([256, 256, 2])
>>> print(torch.nn.functional.one_hot(torch.tensor(np.round(q)).long()).shape)
torch.Size([256, 256, 3])

Hi Roach!

Your print precision is such that a number less that 2. is being displayed
as 2.. Your pytorch .long() conversion truncates this value down to 1
(as expected).

Consider:

>>> import torch
>>> torch.__version__
'2.3.1'
>>> import numpy as np
>>> np.__version__
'1.26.4'
>>> q = np.array ([0.0, 1.00001526, 1.999999999])
>>> q
array([0.        , 1.00001526, 2.        ])
>>> q < 2.0
array([ True,  True,  True])
>>> np.unique (q)
array([0.        , 1.00001526, 2.        ])
>>> np.unique (torch.tensor (q).long())
array([0, 1], dtype=int64)

As an aside, please don’t post screenshots of textual information. Doing
so breaks accessibility, searchability, and copy-paste.

Best.

K. Frank

1 Like

Oh my, you’re absolutely right Frank!
I wasn’t even aware that could happen, turns out my “2.” was in reality 1,9999999995716.
Thanks, apologies for the screenshot I’ll edit it just in case.