Trouble with/Strange behavior of float to int

Godot Version

4.5.1.stable

Question

Hi everyone !
A unexcepted behavior from gdscript is breaking my code.
However, as I’m not the best dev ever, It might be used related

Floats are behaving in a way that I (myself) would have not excepted :

Let’s make an EditorScript

@tool

extends EditorScript

func _init() -> void:
	var test : float = 1.0

	print('My base float')
	print('float test value is ' + str((test)))
	print('int test value is ' + str(int(test)))

	test += 0.40
	test -= 0.40

	print(' ')

	print('After the operation')
	print('float test value is ' + str((test)))
	print('int test value is ' + str(int(test)))

Here are the output :

My base float
float test value is 1.0
int test value is 1
 
After the operation
float test value is 1.0
int test value is 0

Which is quit suprising and might be game breaking.

Is this an specificity from floats to int that i’m missing ?
My first guess is int() is doing a floor() to int, and float is something like 0.999999999999, but i’m not competent enough

Thanks !

I don’t know what result you were expecting. But it’s all correct and how it’s supposed to be.

int int(from: float)

Constructs a new int from a float. This will truncate the float, discarding anything after the floating point.

This means basically, if you cast a float as int, the floating point will be discarded. Some examples.

3.1 → 3
3.9 → 3
-3.1 → -3
-3.9 → -3

1 Like

Also:

Yes, that seems to be correct. You simply can’t rely on 1.0 + 0.4 - 0.4 being exactly 1.0 in a floating point context. If you compare floats you’d have to account for a small margin that the float may differ from what you expect. See info in the docs about floating point precision in Godot.

2 Likes

Thanks you all !

I managed my way out already with snappedf() but that’s enlightening to understand what I wasn’t understanding

3 Likes

The decimal number 0.1 is a repeating fraction in binary …

0.0001100110011 … and the 0011 pattern recurs infinitely.

The computer cannot compute it, that simple.

0.4 in binary is 0.01100110011 …

You should be ok with 0.5