Four is Magic: On Steroids

Four is Magic is a popular math game. You spell out any number into English:

i.e. 117117 = one hundred seventeen

And then you add the total letters together. So 'one hundred seventeen' has 1919 letters.
When we continue this:

i.e. 117198544117 → 19 → 8 → 5 → 4 → 4

It is notable that "four" has exactly 44 letters in it. It is the only number with this quality.


Certain Rules

  • We exclude counting the spaces and hyphens in the name. Only letters.
  • We don't say "one hundred and one". We exclude the "and".

On Steroids

I came up with a bonus feature to this puzzle.
Instead of adding the words count of each word like this:

i.e. 117117 = one hundred seventeen = 3+7+9193 + 7 + 9 → 19

We will be taking the product of each word count:

i.e. 117117 = one hundred seventeen = 3791893 * 7 * 9 → 189

This leads to very different results! 44 is still special, but now are there other numbers with this quality?

Yes, there are!

  • 2424 → twenty four =64=24= 6 * 4 = 24

Can you find the others?

  • Problem 1: I have found 9 solutions for aaa → a
  • Problem 2: I have found 25 other solutions for ab...aa → b → ... → a

If you can find solutions for aaa → a, be sure to post them in this sequence: A058230.

How can you code this problem?
What are the solutions to both problems? My 9th solution is a monstrous 42 digit number!
Are there more than 9 solutions?
What other interesting numbers can you find?

Turns out these numbers are called Fortuitous Numbers.

#NumberTheory

Note by Jonathan Pappas
2 months, 4 weeks ago

No vote yet
1 vote

  Easy Math Editor

This discussion board is a place to discuss our Daily Challenges and the math and science related to those challenges. Explanations are more than just a solution — they should explain the steps and thinking strategies that you used to obtain the solution. Comments should further the discussion of math and science.

When posting on Brilliant:

  • Use the emojis to react to an explanation, whether you're congratulating a job well done , or just really confused .
  • Ask specific questions about the challenge or the steps in somebody's explanation. Well-posed questions can add a lot to the discussion, but posting "I don't understand!" doesn't help anyone.
  • Try to contribute something new to the discussion, whether it is an extension, generalization or other idea related to the challenge.
  • Stay on topic — we're all here to learn more about math and science, not to hear about your favorite get-rich-quick scheme or current world events.

MarkdownAppears as
*italics* or _italics_ italics
**bold** or __bold__ bold

- bulleted
- list

  • bulleted
  • list

1. numbered
2. list

  1. numbered
  2. list
Note: you must add a full line of space before and after lists for them to show up correctly
paragraph 1

paragraph 2

paragraph 1

paragraph 2

[example link](https://brilliant.org)example link
> This is a quote
This is a quote
    # I indented these lines
    # 4 spaces, and now they show
    # up as a code block.

    print "hello world"
# I indented these lines
# 4 spaces, and now they show
# up as a code block.

print "hello world"
MathAppears as
Remember to wrap math in \( ... \) or \[ ... \] to ensure proper formatting.
2 \times 3 2×3 2 \times 3
2^{34} 234 2^{34}
a_{i-1} ai1 a_{i-1}
\frac{2}{3} 23 \frac{2}{3}
\sqrt{2} 2 \sqrt{2}
\sum_{i=1}^3 i=13 \sum_{i=1}^3
\sin \theta sinθ \sin \theta
\boxed{123} 123 \boxed{123}

Comments

Fascinating! I just might try coding this. I'll probably even use this digit-separating formula I came up with a while back.

David Stiff - 2 months, 4 weeks ago

Log in to reply

Thank you! It's a really interesting programming challenge. That's also a very useful formula!

Jonathan Pappas - 2 months, 4 weeks ago

Log in to reply

Phew! 100 lines of code later, and it takes me a minute to reach the fourth OEIS entry. :)

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
# digit seperator
def get_digit(num, place):
    return (num % (10**(place+1))) - (num % (10**place))

# convert numbers between 0 and 1000 to English (used in get_eng_num)
def get_eng_num_under_1000(num):
    # separate digits
    digits = [get_digit(num, place)/(10**place) for place in range(len(str(num)))]
    digits.reverse()

    # create number to English mappings
    singles = {1:"one", 2:"two", 3:"three", 4:"four", 5:"five", 6:"six", 7:"seven", 8:"eight", 9:"nine"}
    powers_of_ten = {10:"ten", 100:"hundred"}

    # create improper English to proper English mappings
    tens_convert = {2:"twenty", 3:"thirty", 4:"forty", 5:"fifty", 6:"sixty", 7:"seventy", 8:"eighty", 9:"ninety"}
    teens_convert = {1: "eleven", 2:"twelve", 3:"thirteen", 4:"fourteen", 5:"fifteen",
                    6:"sixteen", 7:"seventeen", 8:"eighteen", 9:"nineteen"}

    # convert numbers to English
    english_number = []
    size = len(digits)
    # if the number in in the hundreds
    if size == 3:
        # convert hundreds
        if digits[-3] > 0:
            english_number.append(" ".join([singles[digits[0]], "hundred"]))
    # if the number is in the hundreds or tens
    if size >= 2:
        # convert tens, except teens
        if digits[-2] > 1:
            english_number.append(tens_convert[digits[-2]])
            # convert ones
            if digits[-1] > 0:
                english_number.append(singles[digits[-1]])
        # convert teens (except ten)
        elif digits[-2] == 1 and digits[-1] > 0:
            english_number.append(teens_convert[digits[-1]])
        # convert ten
        elif digits[-2] == 1 and digits[-1] == 0:
            english_number.append("ten")
        # convert less than ten
        elif digits[-2] == 0 and digits[-1] > 0:
            english_number.append(singles[digits[-1]])
    # if the number is a single digit
    if len(digits) == 1:
        # convert ones
        if digits[-1] > 0:
            english_number.append(singles[digits[-1]])

    # join and return English number
    return " ".join(english_number)

# convert a number to it's English equivalent
def get_eng_num(num):
    # separate digits, and return only the digit (not the full digit value)
    digits = [int(get_digit(num, place)/(10**place)) for place in range(len(str(num)))]

    # how many groups of three we can make:
    size = round((len(digits) + 1)/3)
    # separate into groups of three
    threes = []
    for i in range(size):
        new_three = [str(d) for d in digits[(3*i):(3*i)+3]]
        new_three.reverse()
        threes.append(int("".join(new_three)))

    # convert each group of three to English and add on appropriate power of 1000
    powers_of_1000 = ["", "thousand", "million", "billion", "trillion", "quadrillion", "quintillion",
                    "sextillion", "septillion", "octillion", "nonillion", "decillion"]
    english_number = []
    for i, three in enumerate(threes):
        if three:
            if i == 0:
                english_number.append(get_eng_num_under_1000(three))
            else:
                english_number.append(" ".join([get_eng_num_under_1000(three), powers_of_1000[i]]))

    # reverse and join it all together, or return "zero" if there's nothing left
    english_number.reverse()
    if english_number:
        return " ".join(english_number)
    else:
        return "zero"

# main function for the "word product"
def compute_word_product(num):
    words = get_eng_num(num).split(" ")
    word_product = 1
    # also returns length of each word for printing later
    word_lengths = []
    for word in words:
        word_product *= len(word)
        word_lengths.append(str(len(word)))

    return word_product, word_lengths

# value to be set \/
for n in range(2000000):
    n_word_product, n_word_lengths = compute_word_product(n)
    if n_word_product == n:
        print(f"{n} -> {get_eng_num(n)} ({' * '.join(n_word_lengths)})")

David Stiff - 2 months, 4 weeks ago

Log in to reply

@David Stiff Wow, that's great! Here is my program: https://github.com/JonnyGamer/FourIsMagicOnSteroids/blob/main/main.py

Jonathan Pappas - 2 months, 4 weeks ago

Does that mean that you found more entries than are listed in the OEIS sequence, or am I reading that wrong?

David Stiff - 2 months, 4 weeks ago

Log in to reply

Yes, I found 3 more, the largest of which has 42 digits. I’m trying to add the new terms to OEIS, but now I am waiting for approval from an editor.

I’m also adding a new sequence focused on numbers of type “a -> b -> ... -> a”. But that one also needs to be approved by an editor.

Jonathan Pappas - 2 months, 4 weeks ago

Log in to reply

Woah, cool! How long did that take?

David Stiff - 2 months, 4 weeks ago

Log in to reply

@David Stiff This program takes less than 5 minutes: https://github.com/JonnyGamer/FourIsMagicOnSteroids/blob/main/main.py

But then no new solutions appeared after 24 hours of running, up to about ~ 10^130

Jonathan Pappas - 2 months, 4 weeks ago

Log in to reply

@Jonathan Pappas Good grief. That's some awesome code. :) That was a good idea generating a cache ahead of time.

David Stiff - 2 months, 4 weeks ago

Log in to reply

@David Stiff Thank you! I'm trying to optimize it, so any tips would be welcome.

Jonathan Pappas - 2 months, 4 weeks ago
×

Problem Loading...

Note Loading...

Set Loading...