Ich habe mit diesem Problem zu kämpfen, das ich in einem wettbewerbsfähigen Programmierbuch gefunden habe, aber ohne eine Lösung, wie es geht. Suchen
Sie für zwei gegebene ganze Zahlen A und B (kann in einen 64-Bit-Integer-Typ passen), wobei A ungerade ist, ein Paar von Zahlen X und Y, so dass A = X * Y und B = X x oder Y. Mein Ansatz war es, aufzulisten alle Teiler von A und versuchen, Zahlen unter sqrt (A) mit Zahlen über sqrt (A) zu paaren, die sich mit A multiplizieren und prüfen, ob ihr xor gleich B ist . Aber ich weiß nicht, ob das effizient genug ist. Was wäre eine gute Lösung / ein guter Algorithmus für dieses Problem?
algorithm
bit-manipulation
Aster W.
quelle
quelle
X*Y
oderX&Y
?Antworten:
Hier ist eine einfache Rekursion, die die uns bekannten Regeln beachtet: (1) Die niedrigstwertigen Bits von X und Y werden gesetzt, da nur ungerade Multiplikanden ein ungerades Vielfaches ergeben. (2) wenn wir X so einstellen, dass es das höchste gesetzte Bit von B hat, kann Y nicht größer als sqrt (A) sein; und (3) Setzen von Bits in X oder Y gemäß dem aktuellen Bit in B.
Der folgende Python-Code führte zu weniger als 300 Iterationen für alle bis auf eines der zufälligen Paare, die ich aus Matt Timmermans Beispielcode ausgewählt habe . Aber der erste dauerte 231.199 Iterationen :)
Ausgabe:
quelle
Sie wissen, dass mindestens ein Faktor <= sqrt (A) ist. Machen wir das eine X.
Die Länge von X in Bits beträgt ungefähr die Hälfte der Länge von A.
Die oberen Bits von X - diejenigen mit einem höheren Wert als sqrt (A) - sind daher alle 0, und die entsprechenden Bits in B müssen denselben Wert haben wie die entsprechenden Bits in Y.
Wenn Sie die oberen Bits von Y kennen, erhalten Sie einen ziemlich kleinen Bereich für den entsprechenden Faktor X = A / Y. Berechnen Sie Xmin und Xmax entsprechend den größtmöglichen und kleinstmöglichen Werten für Y. Denken Sie daran, dass Xmax auch <= sqrt (A) sein muss.
Dann probieren Sie einfach alle möglichen Xs zwischen Xmin und Xmax aus. Es wird nicht zu viele geben, also wird es nicht sehr lange dauern.
quelle
Der andere einfache Weg, um dieses Problem zu lösen, beruht auf der Tatsache, dass die unteren n Bits von XY und X x oder Y nur von den unteren n Bits von X und Y abhängen. Daher können Sie die möglichen Antworten für die unteren n Bits zur Einschränkung verwenden die möglichen Antworten für die unteren n + 1 Bits, bis Sie fertig sind.
Ich habe herausgefunden, dass es leider mehr als eine Möglichkeit für ein einzelnes n geben kann . Ich weiß nicht, wie oft es viele Möglichkeiten geben wird, aber es ist wahrscheinlich nicht zu oft, wenn überhaupt, so dass dies in einem Wettbewerbskontext in Ordnung sein kann. Wahrscheinlich gibt es nur wenige Möglichkeiten, da eine Lösung für n Bits mit gleicher Wahrscheinlichkeit entweder 0 oder zwei Lösungen für n + 1 Bits liefert .
Es scheint ziemlich gut für zufällige Eingaben zu funktionieren. Hier ist der Code, mit dem ich ihn getestet habe:
Sie können die Ergebnisse hier sehen: https://ideone.com/cEuHkQ
Sieht so aus, als würde es normalerweise nur ein paar tausend Schecks dauern.
quelle