Bei einer positiven Zahl n werden alle unterschiedlichen multiplikativen Partitionen von n in einem beliebigen geeigneten Format ausgegeben.
Eine multiplikative Partition von n ist eine Menge von ganzen Zahlen, alle größer als eins, so dass ihr Produkt n ist . Beispielsweise hat 20 die folgenden unterschiedlichen multiplikativen Partitionen:
2 * 2 * 5
2 * 10
4 * 5
20
Die Reihenfolge spielt keine Rolle, so 2 * 2 * 5
ist die gleiche Partition wie 2 * 5 * 2
.
Beispiele:
1 -> {}
2 -> {2}
4 -> {2, 2}, {4}
20 -> {2, 2, 5}, {2, 10}, {4, 5}, {20}
84 -> {2, 2, 3, 7}, {2, 2, 21}, {2, 14, 3}, {2, 6, 7}, {2, 42}, {4, 3, 7}, {28, 3}, {4, 21}, {6, 14}, {12, 7}, {84}
Antworten:
Brachylog , 16 Bytes
Dies ist eine Funktion (kein vollständiges Programm), die eine positive Zahl als Eingabe verwendet und alle multiplikativen Partitionen davon generiert . (Ich habe auch die Verwendung von eingebauten Primfaktoren in dieser Lösung vermieden, hauptsächlich, weil ich nicht sicher war, ob sie helfen würden; ich könnte auch irgendwann eine eingebaute Lösung ausprobieren.)
Probieren Sie es online! (Um die Funktion hier in ein vollständiges Programm umzuwandeln, wurde zusätzlicher Code hinzugefügt. Wenn Sie TIO die oben gezeigte Funktion direkt zur Verfügung stellen, wird die Funktion ausgeführt, die Ausgabe jedoch nirgends gedruckt, was als Demonstration nutzlos ist .)
Dieses Programm ist wirklich enttäuschend für mich, da es hauptsächlich um Fehler im Brachylog-Interpreter und Mängel in seiner Spezifikation geht, anstatt das Problem tatsächlich zu lösen. aber der Dolmetscher ist was er ist. (Selbst mit dem Programm wie diesem verbraucht der Interpreter viel mehr Speicher als es logischerweise sein sollte und stürzt aufgrund von Speichermangel ab, aber zum Glück schafft er es bei kleinen Problemen, zuerst die gewünschte Ausgabe zu erzeugen.) In einer hypothetischen "perfekten Version von Brachylog" Sie könnten einfach schreiben
~*.o.:{>1}a,
, was 4 Bytes kürzer wäre, aber ich musste zusätzliche Einschränkungen hinzufügen, um dem Interpreter ein wenig zu helfen. (Ich mag Brachylog nicht wirklich und würde mich lieber an Prolog halten, aber es brauchte ähnliche Hinweise, damit das Programm funktioniert und sie sind viel länger zu schreiben. Also ist es Brachylog.)Erläuterung:
Wie üblich besteht ein Brachylog-Programm aus einer Reihe von Einschränkungen. Standardmäßig beschränkt die erste Einschränkung die Eingabe auf ein unbekanntes Element (das ich A nennen werde ), die zweite Einschränkung beschränkt A auf ein zweites unbekanntes Element B usw., bis die Ausgabe erreicht ist. Einige Zeichen, wie z. B.
{}
, können diesen allgemeinen Ablauf ändern. Daher verwende ich einen anderen Satz von Buchstaben (z. B. X / Y ), um Unbekannte in verschachtelten Prädikaten darzustellen.Es ist immer noch unklar, wie das Programm funktioniert. Versuchen wir also, die Einschränkungen ein wenig zu vereinfachen. C , D , G , H und ich sind alle gleich (und gleich der Ausgabe). E und F sind auch gleich (und gleich der Eingabe). Unsere Einschränkungen beschränken sich also auf Folgendes:
:{1<}a
das linke Argument eine begrenzte Länge haben muss oder der Interpreter in eine Endlosschleife gerät).Übrigens habe ich nicht explizit angegeben, dass alle Elemente der Ausgabe Ganzzahlen sind. Dies scheint erforderlich zu sein. Brachylogs Constraint-Solver kann jedoch keine Nicht-Ganzzahlen verarbeiten, sodass nur die Lösungen erstellt werden, die Ganzzahlen enthalten.
Offensichtlich ist "die Länge der Ausgabe kleiner als die Eingabe" immer dann wahr, wenn die Ausgabe eine multiplikative Partition der Eingabe ist (weil 2 x > x für alle nichtnegativen x , dh positive 2 x ). Wir können diese Einschränkung also ignorieren. Es dient nur dazu, dem Brachylog-Dolmetscher eine Arbeitsstrategie für die Bewertung des Programms zu geben. Die anderen Einschränkungen (dass die Ausgabe sortiert ist, dass ihr Produkt die Eingabe ist und dass ihre Elemente alle größer als 1 sind) sind die Definition einer multiplikativen Partition, und daher ist diese Funktion im Grunde nur eine direkte Implementierung der Frage.
quelle
Brachylog 1, 14 Bytes
Probieren Sie es online!
Brachylog 2,
1110 Bytes, SprachnachstellungProbieren Sie es online!
Maltysen beantwortete diese Frage in 17 Byte Pyth, und ich fand eine 16-Byte-Brachylog-Lösung, bei der die Spezifikation der Frage in Brachylog übersetzt wurde. Während ich das tat, schrieb Dennis eine 15-Byte-Jelly-Lösung. Also musste ich auf 14 Bytes runter. Dies ist eine Funktion , die die Eingabe als Argument verwendet und eine Liste aller Partitionen zurückgibt (und nicht wie bei meiner anderen Lösung einen Generator).
Einige Zeit, nachdem ich diese Antwort geschrieben hatte, gelang es Dennis und mir, die Jelly-Lösung auf 11 Byte zu reduzieren. Es stellt sich heraus, dass es eine neue Version von Brachylog gibt, mit einer terseren Syntax. Es datiert die Challenge nach, zählt also eigentlich nicht, könnte aber die 11-Byte-Summe zu sehr verwalten, sobald es veröffentlicht wird. Spätere Überarbeitungen der Sprache (inspiriert von anderen Herausforderungen) können, wie hier zu sehen, bis zu 10 betragen. Die beiden Programme sind identisch, der einzige Unterschied besteht in der Syntax.
Im Gegensatz zu meiner anderen Lösung, die nicht viel von "Golf-Primitiven" Gebrauch machte, sondern das Problem direkt ansprach, ignoriert diese so gut wie die gesamte Kraft der Brachylog-Einschränkungen und gibt stattdessen den besten Jelly-Eindruck ab und schreibt eine Kette von Einschränkungen, für die Das linke Argument ist bereits bekannt (und daher wirken die Einschränkungen einfach wie Jelly-Monaden und nicht wie ausgereifte Einschränkungen). Es wird daher derselbe Algorithmus wie bei der Pyth-Lösung von @ Maltysen verwendet, was wahrscheinlich der einfachste Weg ist, dies unter Verwendung typischer Golf-Primitive zu lösen. (Interessanterweise wäre die "Just State the Problem" -Lösung in meiner anderen Antwort kürzer, wenn der Brachylog-Interpreter keine Bugs / Mängel aufweist, obwohl er keine Golf-Primitive verwendet. Eines Tages muss ich ein "verbessertes Brachylog" schreiben. um eine gute Lösung für diese Art von Problem zu finden; Brachylog ist, was Golfsprachen angeht, eigentlich sehr ausführlich.)
Das Programm besteht aus einem Generator und einem Wrapper. Hier ist zunächst eine Erklärung des Generators:
Damit ist das Problem fast gelöst, aber am Ende werden viele Partitionen mehrmals generiert. Wir brauchen also einen Wrapper, um die Lösungen zu deduplizieren:
quelle
Mathematica, 61 Bytes
Definiert einen (rekursiven) unären Operator,
±
der die Liste der Partitionen zurückgibt.quelle
Pyth - 17 Bytes
Nimmt alle Permutationen der Primfaktorisierung, partitioniert dann jede Partition und erzeugt dann alle Partitionen, behält dann nur verschiedene Partitionen bei.
Test Suite .
quelle
Python 2, 70 Bytes
Gibt eine Liste sortierter Listen aus. Zum Beispiel
f(20)
ist[[2, 2, 5], [2, 10], [4, 5], [20]]
.quelle
O(n)
und Vergleich mit dem Python 2-Konkurrenten könnte mehrO(n^4)
Stil sein - während f (998) Speicher sprengen könnte oder Hardware während des Laufs abstürzen könnte Zeit von ca. 80 Tagen mit dem anderen Algorithmus konvergiert dieser hier nach ca. 7 Millisekunden auf meiner Maschine, um das Ergebnis zu erzielen[[2, 499], [998]]
. IMO könnte das Problem mehr sein, dass fürN > 998
dieRecursionError: maximum recursion depth exceeded in comparison
Stopps der oben genannte Python 3-Code ... Viel Spaß beim Golfen :-)O(n^4)
für meine Python2-Übermittlung ausreicht: D Unter Berücksichtigung des Testfalls 998 wird mein Code neunmal ausgeführt und die(n+r-1)! / r! / (n-1)!
Anzahl der Tupel jedes Mal berechnet , wenn err
linear von 2 auf n ansteigt9 - 2
. Aber hey, zumindest müssen Sie das Rekursionslimit nichtJelly ,
141311 BytesProbieren Sie es online!
Ich war mir ziemlich sicher, dass die Lösung von @ Dennis's Jelly verbessert werden könnte. Leider habe ich es nicht geschafft, den Brachylog-Rekord zu schlagen, aber ich habe es geschafft, ihn zu binden. Update : Mit Hilfe von @Dennis wurde es jetzt verbessert. Ich denke, Jelly nimmt die Krone zurück.
Dieses Programm ist unglaublich ineffizient und hat eine O (2 n 2 ) -Leistung (weshalb der obige Testfall dies für Eingabe 4 zeigt). Es endet schnell bei 4, sehr langsam bei 5, und es ist möglicherweise praktisch nicht möglich, für größere Zahlen zu laufen.
Interessanterweise wurde das Brachylog verbessert, indem von einer Lösung, die das Problem beschrieb (in der Brachylog gut ist), zu einer Lösung übergegangen wurde, die einen Algorithmus verwendete, der auf der Faktorisierung der Eingabe basierte (in der Jelly gut ist). In der Zwischenzeit wurde die Gelee-Lösung verbessert, indem man sich von ihren Stärken entfernte und zu einer Lösung zurückkehrte, die nur das Problem beschreibt.
Erläuterung:
Da die Ausgabe von
Ḋx
sortiert ist, muss jede Untersequenz auch sortiert werden, sodass wir sie nicht einzeln sortieren müssen. Der Teil "Dieselbe Ausgabe in verschiedenen Reihenfolgen ist ein Duplikat" des Problems und der Teil "Alle Werte in der Ausgabe sind> 1" des Problems wird von der Generation gelöst. Abgesehen davon geht es hier im Grunde genommen darum, "alle Listen zu finden, für dieP=³
", was wir (auf unglaublich ineffiziente Weise) tun , indem wir alle fraglichen Listen generieren und dann die falschen herausfiltern.(Es ist klar, dass jemand eine Mischung aus Jelly und Brachylog sowie einen wirklich guten Beschränkungslöser erfinden muss , damit wir etwas in der Art von
{P=³}~
Deduplizierungscode schreiben und das Programm in einer viel kürzeren Länge lösen können. Das könnte sein in einiger Entfernung.)quelle
2r
Kann werdenḊ
, undP=³$$
kann werdenP=¥
.P=¥
funktioniert nicht , wenn ich es in den Dolmetscher versuchen, obwohl ich bin mir nicht ganz sicher , warum (logisch, es sollte funktionieren, und es war eines der Dinge , die ich versuchte , während die Post zu schreiben, ich habe gerade versucht wieder sicher zu machen, es macht definitiv nicht das, was ich erwartet hatte).Ḋ
Ich denke, es gibt unsere Ein-Byte-Einsparung :-)µ
mit¹
als auch, wieµ
macht den wiederholten Bereich das neue linke Argument.³
eher als¹
nur für die Sorte.)JavaScript (ES6),
7467 ByteLöst das Problem direkt rekursiv: Für jede ganze Zahl m von 2 bis n nehmen wir jede der Partitionen von n / m mit einem minimalen Element von m (um doppelte Partitionen zu vermeiden) und hängen m an . (Für jedes m , das n nicht teilt , ergibt dies das leere Array, da sich keine Anordnung von ganzen Zahlen mit einer Dezimalstelle multipliziert.) Wir definieren einen Basisfall des leeren Arrays für 1 , um eine unendliche Rekursion zu vermeiden.
quelle
Python2,
198191172180 BytesEin volles Programm. Dies könnte erheblich verbessert werden, daher sind Vorschläge herzlich willkommen!
Ausgänge von 1 bis einschließlich 31:
quelle
4 -> {2, 2}, {4}
, eine solche Ausgabe wird in Ihrem Protokoll nicht angezeigt.int(math.log(n,2))
, was das verursachte. +2 Bytes und es wird funktionieren. Vielen Dank!math
aber verwendenmath.log
.len(bin(n))-2
ist es kürzer alsint(math.log(n,2))
.Gelee , 15 Bytes
Probieren Sie es online!
quelle
Clojure, 91 Bytes
Beispiel läuft:
Der Wert selbst wird als einzelne Zahl (nicht als a
list
) zurückgegeben, andere werden als Listen ausgegeben. Dasn
am Ende könnte ersetzt werden[n]
, um es auch zu einer Sequenz oder(list n)
zu einer Liste zu machen.quelle
Wolfram Language (Mathematica) ,
585652 BytesProbieren Sie es online!
Angepasst von meiner Mathematica-Lösung an Dividing Divisive Divisors . Gibt eine
Sequence
der Partitionen zurück.quelle
J, 35 Bytes
Basierend auf Lösung einer zeitlich begrenzten Faktorisierungsaufgabe.
Diese Version ist viel ineffizienter und läuft in Fakultätszeit basierend auf der Anzahl der Primfaktoren. Erstellt Partitionen durch Generieren von Fakultätszahlen.
Probieren Sie es online!(Versuchen Sie nicht große Werte online!)
Erläuterung
quelle
D, 95 Bytes
Nur eine rekursive Lösung. In
g(n,r)
,r
ist die Partition bisher undn
der Wert, der noch in Faktoren zerlegt werden muss. Um jede ungeordnete Partition nur einmal zu erhalten, sortieren wir die Faktorenr
in nicht aufsteigender Reihenfolge. Das letzte Element vonr
beginnt mit2
dem kleinstmöglichen Faktor und wirdn
in jeder Kopie unmittelbar vor jeder Ausgabeoperation überschrieben .Für
n = 60
ist die Ausgabe wie folgt:Probieren Sie es online!
quelle
void g(T)(T n,T[]r){for(T i=r[0];i*i<=n;i++)n%i0:r;r.back=n;r.writeln;}g(n,[2])
std.stdio
undstd.range
Eingaben1
nichts ausgeben sollten, nicht[1]
.D, 109 Bytes
Probieren Sie es online!
quelle