#(Int to Float) Turn X into 0.X

1 messages · Page 1 of 1 (latest)

orchid folio
#

I want to Mathematically find a way to turn X into 0.X as I assume it is better that way? Of course the obvious way is to turn it into a string and parseFloat kinda thing but I wonder if there's a better way to do that, I assumed math will be handy here (For example I'd like 274 to turn into 0.274)

twin abyss
#

parseFloat - this is JS function but your post is tagged C#

orchid folio
#

float.Parse

twin abyss
#

gotcha

orchid folio
#

just generally pointed out the idea

twin abyss
#

Something like x / pow(10, floor(log10(abs(n)))+1) for any non-zero n

orchid folio
#

do you think this solution would prove better than the string one?

#

it sure isn't cleaner

twin abyss
#

much

orchid folio
#

but yeah I've once looked into an integer parsing method and it is long and loopy

twin abyss
#

floor(log10(abs(n)))+1 - this formula calculates how many digits a number has. so for 123, it'll return 3. for 9 it'll return 1. for 1000 it'll return 4

orchid folio
#

I assume floats are even worse

twin abyss
#

no wait abs duh

#

it works for n < 0, just not n = 0

#

but you could just add in a case for that and if n = 0, the digit count is obviously just 1

orchid folio
#

so I'd have to check 0 as an exception?

#

yeah

twin abyss
#

oh you might need to +2 actually

#

because you need one more digit than the number of digits in the original number

#

essentially you want to get the value 1000 from a 3 digit number like 274. because then you do 274 / 1000, which gives you 0.274

#

no wait. 1 followed by as many zeroes as there are digits kekw so +1 is fine

twin abyss
orchid folio
#

Yeah the parsing methods look ugly and logically speaking are prob more time consuming

orchid folio
twin abyss
#

oh oops

#

yeah

#

I changed one and forgot to change the other

#

x=n, just a typo

orchid folio
#

yeah gotcha

#

thanks :3

twin abyss
#

Writing up benchmarks now

#

string version vs math

orchid folio
#

ooh I wanna see how much better that is

#

I've built many many lexers and parsers in the past and I am just experimenting with different ways to make them, which are hopefully easier / more maintainable / more performant and kinda wanna see where I find my best balance between the three

#

THAT I wanna benchmark later lol

twin abyss
#

Okay, these are my two methods

[Benchmark]
[Arguments(274)]
public float UsingToStringAndParse(int value)
{
    return float.Parse($"0.{value}");
}

[Benchmark]
[Arguments(274)]
public float UsingDivide(int value)
{
    if (value == 0)
    {
        return 0;
    }

    return value / MathF.Pow(10, MathF.Floor(MathF.Log10(MathF.Abs(value))) + 1);
}
#

I already know the string version is going to cost an allocation

#

but I'm actually more interested in speed here

#

Okay yeah, as expected. Much faster. And also no allocations

|                Method | value |     Mean |    Error |   StdDev | Allocated |
|---------------------- |------ |---------:|---------:|---------:|----------:|
| UsingToStringAndParse |   274 | 93.47 ns | 1.084 ns | 0.961 ns |      32 B |
|           UsingDivide |   274 | 20.39 ns | 0.092 ns | 0.077 ns |         - |
#

Hope that helps @orchid folio

#

I was doubtful because of the Pow call, because Pow is not that performant. But looks like my worry was misplaced, runs just fine

orchid folio
#

yeah that's quite the difference

#

nearly 5 times over

#

wait

#

oop I feel dumb seeing multiple numbers and not knowing which one directly corrolates to time

twin abyss
#

Mean

#

that's the one for time

#

Error is just error margin, StdDev is standard deviation, not terribly important

orchid folio
#

Oh wait I didn't see the headers

twin abyss
#

Mean and Allocated are the two important columns

#

Pure-math solution is both faster, and more memory efficient

orchid folio
#

yeah nearly 5 times faster

#

wow

orchid folio
twin abyss
#

You're welcome!

orchid folio
#

On another note

#

assuming I have a string which I 100% is a valid int..

#

is there a better way to parse it? such as iterating over characters and do val *= 10; val += char.GetCharacterDigit(c); (not sure if that's exactly the method's name)

twin abyss
#

char.GetNumericValue, but no, that is much much worse

orchid folio
#

really? I figured because int.Parse checks the validity of the string it'd be worse

twin abyss
#

well yeah, you want that to happen

#

2⅜9 isn't a valid integer, but using your supposed solution it would parse "fine"

orchid folio
#

I see