[RUBY] Finden Sie den Rest geteilt durch 3, ohne eine Zahl zu verwenden

Thema

Definieren Sie eine Funktion oder Methode, die eine Ganzzahl größer oder gleich 0 als ** Zeichenfolge ** und den Rest nach Division durch 3 zurückgibt. Dieser Artikel verwendet Ruby, es ist also eine Methode.

Es wird jedoch kein numerischer Wert verwendet. Verwenden Sie also keine numerischen Objekte während der Verarbeitung. Selbstverständlich ist der Rückgabewert auch eine Zeichenfolge.

Ich weiß nicht, ob die integrierte Methode intern ein numerisches Objekt erstellt hat, daher gehe ich davon aus, dass der von mir geschriebene Code kein numerisches Objekt in der Mitte erstellt.

Nennen wir die Methode "rest_modulo_3". Ich bin nicht sicher, ob das Englisch korrekt ist, aber der Rest ist der Rest, und Modulo 3 bedeutet "wenn durch 3 geteilt" [^ Modulo 3].

[^ modulo3]: modulo 3 soll formal 3 mathematisch "3 als Gesetz" sein.

Es sollte so aussehen:

p remainder_modulo_3("0")  # => "0"
p remainder_modulo_3("8")  # => "2"
p remainder_modulo_3("12") # => "0"
p remainder_modulo_3("22") # => "1"

Wie man es von Hand macht

Bevor Sie über das Programm nachdenken, sollten Sie es manuell ausführen.

Zum Beispiel kann der Rest von 1234567 geteilt durch 3 auf einen Blick als 1 gesehen werden. wie? Was meinst du?

Betrachten Sie zunächst den Rest des einfacheren 87 geteilt durch drei. Sie können die Teilung ernsthaft durchführen, aber es gibt eine Möglichkeit, mehr zu überspringen.

\begin{eqnarray}
87 &=& 8 \times 10 + 7 \\
   &=& 8 \times (9 + 1) + 7 \\
   &=& 8 \times 9 + 8 + 7
\end{eqnarray}

$ 8 \ times 9 $ ist jedoch ein Vielfaches von $ 9 $, daher ist es durch $ 3 $ teilbar. Daher können Sie $ 8 \ times 9 $ ausschließen und den Rest von $ 8 + 7 $ geteilt durch $ 3 $ finden.

Da $ 8 + 7 $ $ 15 $ ist, ist es durch $ 3 $ teilbar. Der Rest ist $ 0 $.

Genauso denken, auch eine große Zahl wie 1234567

\begin{eqnarray}
1234567 &=& 1 \times (999999 + 1) + 2 \times (99999 + 1) + 3 \times (9999 + 1) + 4 \times (999 + 1) + 5 \times (99 + 1) + 6 \times (9 + 1) + 7 \\
  &=& (Vielfaches von 9) + 1 + 2 + 3 + 4 + 5 + 6 + 7
\end{eqnarray}

Daher können Sie den Rest von $ 1 + 2 + 3 + 4 + 5 + 6 + 7 $ geteilt durch $ 3 $ finden.

Sie müssen $ 1 + 2 + 3 + 4 + 5 + 6 + 7 $ nicht ernsthaft berechnen.

(1 + 2) + (3) + (4 + 5) + (6) + 7

Da Sie ein Vielfaches von $ 3 $ sehen können, können Sie $ 1 $ erhalten, indem Sie diese ausschließen und den Rest von $ 7 $ geteilt durch $ 3 $ finden.

Was ist also mit Zahlen wie $ 78932705 $? Anstelle dieser Nummer

7 + 8 + 9 + 3 + 2 + 7 + 0 + 5

Von diesen Zahlen sind 9 $, 3 $ und 0 $ ein Vielfaches von 3 $, sodass Sie sie ausschließen können.

7 + 8 + 2 + 7 + 5

Denken Sie nur darüber nach. Unter Berücksichtigung von $ 7 = 2 \ mal 3 + 1 $ wurde $ 7 $ durch $ 1 $ ersetzt, $ 8 $ wurde durch $ 2 $ ersetzt und $ 5 $ wurde durch $ 2 $ ersetzt.

1 + 2 + 2 + 1 + 2

Sie müssen nur darüber nachdenken. (Die Zahlen, die herauskommen, können nur 1 und 2 sein)

Menschen können dies schnell erkennen und $ 1 $ mit $ 2 $ kombinieren, um $ 3 $ zu machen und es auszuschließen, und der Rest ist sofort als $ 2 $ bekannt. Aber wie geht das programmgesteuert?

Immerhin sortieren

1 + 1 + 2 + 2 + 2

Dann wäre es besser, die Zeichenkette "11222" zu machen.

Danach sollten Sie die Zeichenfolgen wie "111", "222" und "12" löschen.

Code

Ich habe das getan:

def remainder_modulo_3(number)
  s = number.delete("0369").tr("4578", "1212")
    .chars.sort.join
    .gsub(/(.)\1\1|1122|12/, "")
  {"" => "0", "1" => "1", "11" => "2", "2" => "2", "22" => "1"}[s]
end

Gibt eine Ganzzahl größer oder gleich 0 als Zeichenfolge an und gibt eine von "0", "1" und "2" als Zeichenfolge zurück.

Lass es uns versuchen:

1000000.times do |n|
  puts n unless (n % 3).to_s == remainder_modulo_3(n.to_s)
end

Vergleichen Sie die mit Integer berechnete normalerweise mit der mit der Methode rest_modulo_3 erhaltenen und zeigen Sie sie an, wenn sie nicht übereinstimmen. Als ich es versuchte, wurde nichts angezeigt, daher scheint der Code zu stimmen.

Kommentar

Die Methodenkette ist etwas lang, aber was wir tun, ist einfach.

Zuerst

delete("0369")

Da jedoch 0, 3, 6 und 9 Vielfache von 3 sind, werden diese Zahlen ausgeschlossen.

Nächster

tr("4578", "1212")

Zum Beispiel kann 4 durch 1 ersetzt werden, da 4 3 + 1 ist und 5 durch 2 ersetzt werden kann.

Nächster

chars.sort.join

Unterbricht zuerst die Zeichenfolge Zeichen für Zeichen, sortiert sie und verbindet sie erneut. Dies ergibt zum Beispiel "122" aus "212".

Die an diesem Punkt erhaltene Zeichenfolge ist "0 oder mehr" 1 ", gefolgt von 0 oder mehr" 2 "". Es kann kein anderes Muster geben.

Nächster

gsub(/(.)\1\1|1122|12/, "")

Löscht bestimmte Zeichenfolgen in der Reihenfolge von links, aber der reguläre Ausdruck ist etwas verwirrend.

Das Highlight ist der Teil (.) \ 1 \ 1. Dies verwendet eine Rückreferenz. Dies bedeutet, dass zwei von (.) Erfasste Zeichen folgen und insgesamt "drei gleichen Zahlen in einer Reihe" entsprechen.

Es stimmt auch mit den "1122" und "12" überein, die an der Grenze zwischen den Spalten "1" und "2" existieren können.

Diese werden gelöscht.

Welche Art von Zeichenfolge kann nach dieser Konvertierung erhalten werden? Es ist ein bisschen langweilig, aber lassen Sie uns nach der Nummer "1" klassifizieren.

Erstens, da "111" zuerst gelöscht wird (weil mehrere "1" von 3 gelöscht werden), wenn die Zahl von "1" nur 0, 1, 2 ist. Ich weiß, dass es gut ist.

Wenn "1" 0 ist, ist dies eine Zeichenfolge, in der 0 oder mehr "2" verbunden sind. Wenn man bedenkt, dass Vielfache von 3 "2" gelöscht werden, kann es drei geben, "" "," 2 "und" 22 ".

Als nächstes, wenn es eine "1" gibt, wenn 0 "2" folgt, ist es "1", und wenn es eine "2" gibt, ist es das Ganze ("12"). Wird gelöscht, um "" zu werden, und wenn es zwei "2" gibt, wird es zu "2". Wenn es 3 oder mehr "2" gibt, wird "222" gelöscht, sodass Sie nicht darüber nachdenken müssen (die Möglichkeiten sind erschöpft). Mit anderen Worten, es kann drei geben: "1", "" "und" 2 ".

Wenn es schließlich zwei "1" gibt, wenn 0 "2" folgt, ist es "11", und wenn es eine "2" gibt, wird die "12" gelöscht. Es wird "1", und wenn es zwei "2" gibt, wird das Ganze ("1122") gelöscht und es wird eine leere Zeichenfolge. Wenn es drei "2" gibt, wird "1122" gelöscht und wird zu "2". Sie müssen nicht an vier oder mehr denken. Mit anderen Worten, es kann vier geben, "11", "1", "", "2".

Huh, es war nervig.

Immerhin ist die konvertierte Zeichenfolge

Es gibt nur fünf Möglichkeiten.

Zu viel darüber zu reden. das ist alles.

Anwendung

Der Rest nach dem Teilen durch 9 kann genauso erfolgen.

Der Rest nach dem Teilen durch 2 oder 5 muss nur die letzte Ziffer (die Stelle von 1) sehen (da 10 durch 2 oder 5 teilbar ist).

Schauen Sie sich für den Rest geteilt durch 4 die letzten beiden Ziffern an (da 100 durch 4 teilbar ist).

Schauen Sie sich die letzten 3 Ziffern für den Rest geteilt durch 8 an (weil 1000 durch 8 teilbar ist).

Der Rest nach dem Teilen durch 6 sollte ziemlich verwirrend sein. Ich möchte es eines Tages versuchen.

Ich bin nicht sicher, ob der Rest nach dem Teilen durch 7 berechnet werden kann, ohne ein numerisches Objekt zu erstellen.

Schließlich

Selbst wenn mich jemand fragt: "Na und?" Ich habe es als "Integer-Theorie" markiert, aber es ist keine so große Sache, es ist nicht praktisch und es ist nicht sehr interessant. Ich habe nur darüber nachgedacht und es versucht.

Recommended Posts

Finden Sie den Rest geteilt durch 3, ohne eine Zahl zu verwenden
Finden Sie mit Kotlin die Anzahl der Tage in einem Monat
Lassen Sie uns eine Kombination ohne Duplizierung erstellen. | Berechnen Sie zunächst die Gesamtzahl
Richten Sie eine Wordpress Docker-Umgebung ein, ohne das Worpdress-Image zu verwenden
Schreiben Sie einen Nullfall mit dem Typ Optional, ohne die if-Anweisung zu verwenden
Finden Sie den Unterschied von einem Vielfachen von 10
[Android] Erstellen Sie ein Schiebemenü ohne Verwendung der Navigationsansicht
Finden Sie die Fibonacci-Nummer mit dem Fork / Join Framework
Wenn Sie eine vollständige äußere Verknüpfung ausführen, ohne die vollständige äußere Verknüpfung zu verwenden
[Rails] Verwenden Sie das Pulldown-Feld, um die Post-Liste nach Datum oder Anzahl der Likes zu sortieren.
So verbinden Sie eine Tabelle ohne DBFlute und SQL
Bedingte Verzweigung mit fließender Schnittstelle
[Android] Erstellen Sie ein Schiebemenü ohne Verwendung der Navigationsansicht
Wenn Sie eine vollständige äußere Verknüpfung ausführen, ohne die vollständige äußere Verknüpfung zu verwenden
Finden Sie den Rest geteilt durch 3, ohne eine Zahl zu verwenden