Discuss Scratch

rainierroitayam
Scratcher
100+ posts

Converting from Decimal to Base-9

I'm trying to make a base-10 to base-9 converter for my cloud project. This usually works, although sometimes with large base-10 numbers like 31415 it outputs a wrong value. If you are wondering here's the script i'm using: (The output is the variable named “base9”)
definedectobase9setcount2todecsetbase9torepeatuntilcount2=0setcount1to1repeatuntilnot9<count2/count1setcount1tocount1*9setbase9tojoinbase9floorofcount2/count1setcount2tocount2-floorofcount2/count1-count1
Here is what's supposed to be going on: (100 is an example)
Base9 (Output) =
Input = 100
100 / 9^0 = 100 (too big, should be = or < than 9)
100 / 9^1 = 11.111… (too big)
100 / 9^2 = 1.235… (OK)
floor(1.235…) = 1
Base9 = 1
100 - 9^2 = 19
19 / 9^0 = 19 (too big)
19 / 9^1 = 2.111… (OK)
floor(2.111…) = 2
Base9 = 12
19 - 9^1 = 10
10 / 9^0 = 10 (too big)
10 / 9^1 = 1.111… (OK)
floor(1.111…) = 1
Base9 = 121
10 - 9^1 = 1
Output: 121

Last edited by rainierroitayam (April 17, 2017 05:32:57)

RokCoder
Scratcher
1000+ posts

Converting from Decimal to Base-9

Your algorithm has problems if any resulatant digit should be zero.

Let's do this in terms of converting a base 10 number to a base 10 number using your alhorithm (and, yeah, it's pointless but it helps to explain). Let's use 12074 as an example. First you're finding count1 to be 10000 and adding “1” to the output string. Then you're finding count1 to be 1000 and adding “2” to the output string. But that leaves us with 074 so you're finding count1 to be 10 which adds “7” to the string and then, finally, you'll find count1 to be 1 and add 4 to the string. So your conversion would give “1274” rather than “12074”.

I'm assuming the last line was a typo and should have been

setcount2tocount2-floorofcount2/count1*count1

Last edited by RokCoder (April 17, 2017 06:44:04)

awesome-llama
Scratcher
1000+ posts

Converting from Decimal to Base-9

Why base 9? Hexadecimal (base16) is more efficient.
TheLogFather
Scratcher
1000+ posts

Converting from Decimal to Base-9

Don't bother converting from base 10 for storing in the cloud.

I'm guessing you're doing that because you want to have a digit to use as a ‘separator’ – i.e. so you know when you reach the end of a particular set of digits.
(If that's not why you're doing this, then you can ignore everything I'm saying… )


OK, so here are two better alternatives…

1) Use a length indicator instead. (This assumes you are storing only integer values.)
So you have a digit at the start which gives how many digits there are to read in this integer value. So, for example:
“587654310045000” would split up as five digits “87654”, then three digits “100”, then four digits “5000”.
(If you might have values longer than nine digits, then you could use a prefix digit of zero as a continuation – i.e. to say that the next chunk of digits should join on to the previous – or something like that…)

2) Use hex, and have characters A-F for non-digit characters such as dot, minus, “e” (if you have floating-point values).
So, for example “2A345FB500F1A5EB4F” would mean “2.345”, followed by “-500”, then “1.5E-4” – where “A” means dot, “B” means minus, “E” remains as “E”, and “F” is used as the separator/end-of-string.
Note that you have to prefix a hex value with “0x” for it to be accepted as a numerical value – so the example above would end up being the string “0x2A345FB500F1A5EB4F”.

Hope that makes sense!

Last edited by TheLogFather (April 17, 2017 10:57:49)

keme6206
Scratcher
33 posts

Converting from Decimal to Base-9

Build the number from the lowest order digit (right to left)
defineconvert2base9base10numbersetnextdigittosetBase9numbertorepeatuntilbase10number=0setnextdigittobase10numbermod9setBase9numbertojoinnextdigitBase9numbersetbase10numbertobase10number-nextdigit/9

Not much work needed to convert this to a general “base n” conversion for n<10. Do you see how?

Last edited by keme6206 (April 17, 2017 11:16:25)

RokCoder
Scratcher
1000+ posts

Converting from Decimal to Base-9

I was just fixing the algorithm rather than implementing a better one or considering the use case. It was fun to do but not as useful as the suggestions above
TheLogFather
Scratcher
1000+ posts

Converting from Decimal to Base-9

Here's a third alternative (still assuming you're doing this 'cos you want to know when you reach end of string)

3) Have a digit which acts like an 'escape character'.

The digit which follows this ‘special digit’ would then tell you what the meaning is.

So let's say you choose the digit ‘9’ to be the escape character. Then whenever it comes across a ‘9’ in the encoding, you look at the next character, and that tells you what the actual next thing is meant to be – so, it could mean it's a ‘real’ digit 9, or it's the end of the string, or a non-digit character such as a dot, or minus, or “e”.

For example, the value “1.98765e-4” could be stored as “1919987659293490”, where I've used “91” to mean dot, “99” to mean just “9”, “92” to mean “e”, “93” to mean minus, and “90” to mean it's the end of the string – while all other digits need no translation.

Last edited by TheLogFather (April 17, 2017 10:54:52)

rainierroitayam
Scratcher
100+ posts

Converting from Decimal to Base-9

TheLogFather wrote:

Don't bother converting from base 10 for storing in the cloud.

I'm guessing you're doing that because you want to have a digit to use as a ‘separator’ – i.e. so you know when you reach the end of a particular set of digits.
(If that's not why you're doing this, then you can ignore everything I'm saying… )


OK, so here are two better alternatives…

1) Use a length indicator instead. (This assumes you are storing only integer values.)
So you have a digit at the start which gives how many digits there are to read in this integer value. So, for example:
“587654310045000” would split up as five digits “87654”, then three digits “100”, then four digits “5000”.
(If you might have values longer than nine digits, then you could use a prefix digit of zero as a continuation – i.e. to say that the next chunk of digits should join on to the previous – or something like that…)

2) Use hex, and have characters A-F for non-digit characters such as dot, minus, “e” (if you have floating-point values).
So, for example “2A345FB500F1A5EB4F” would mean “2.345”, followed by “-500”, then “1.5E-4” – where “A” means dot, “B” means minus, “E” remains as “E”, and “F” is used as the separator/end-of-string.
Note that you have to prefix a hex value with “0x” for it to be accepted as a numerical value – so the example above would end up being the string “0x2A345FB500F1A5EB4F”.

Hope that makes sense!

Oh thanks for that trick for Cloud Data. I know already that cloud data can support hexadecimal but i have no idea how to make it read in hexadecimal instead of decimal. (It's the “0x” thing you add at the start)

Powered by DjangoBB