Guten Abend,
ich weiß das:
[autoit]Mod(30^37, 77)
[/autoit]
= 2 ist.
Als Ergebnis bekomme ich aber ~ 2,72*10^38 ![]()
Wieso?
Vielen Dank,
Aquaplant
Guten Abend,
ich weiß das:
[autoit]Mod(30^37, 77)
[/autoit]
= 2 ist.
Als Ergebnis bekomme ich aber ~ 2,72*10^38 ![]()
Wieso?
Vielen Dank,
Aquaplant
Weit zu große Zahlen, weil erst die Potenz berechnet wird. Die ist aber in AutoIt bei Weitem nicht darstellbar. Du müsstest eine eigene Mod-Funktion schreibt, die gleich mit reduziert… Material liefert Wikipedia, fast modular exponentiation.
Johannes
Das ist schlecht, da die Zahl noch vergleichsweise superwinzig ist...
Dann werd ich mir wohl selbst die Funktion mit BigInt schreiben müssen.
Vielen Dank für die schnelle Antwort ![]()
Edit: Oha, das wird schwieriger als ich dachte, denn _BigNum_Pow() spuckt auch nur wieder eine ungenaue Zahl aus. Ich schau mir mal das mit Wikipedia an ![]()
Vielleicht verstehe ich das Grundproblem nicht ganz aber mit der >>BigNum.au3<< kommt bei mir problemlos 2 heraus:
[autoit]#include "BigNum.au3"
[/autoit][autoit][/autoit][autoit]MsgBox(0,"",_BigNum_Mod(_BigNum_Pow(30,37), 77))
[/autoit]Perfekt - Vielen Dank, dass erspart mir einiges an Zeit ![]()
Äh, ist der Wertebereich dieser DLL wirklich groß genug? Das ist auch nur ein normaler DWORD.
Hab jetzt mal schnell den 1. Pseudocode von Wikipedia geholt:
Func _ModPow($base, $power, $modulus)
; Wikipedia
If Not (IsInt($power) Or StringIsInt($power)) Or $power < 0 Then Return SetError(1,0,0)
If $base = 0 Then Return 0
Local $c = 1
For $i = 1 To $power
$c = Mod($c*$base, $modulus)
Next
return $c
EndFunc
MsgBox(0, '', _ModPow(30, 37, 77))
[/autoit]Äh, ist der Wertebereich dieser DLL wirklich groß genug? Das ist auch nur ein normaler DWORD.
Für 30 ^ 37 reicht ein DWORD noch, ich weiß halt nicht wie groß seine Zahlen werden...
DWord sollte eben nicht ausreichen: >>Klickmich<<
So oder so wäre die Dll aber nicht der begrenzende Faktor sondern wieder, wie am Anfang, AutoIt da du ja die Potenz erst von AutoIt berechnen lässt und dann das Ergebnis (was AutoIt nicht darstellen kann!) an die Dll übergibst:
$Ret = DLLCall("Mod.dll", "int:cdecl", "ModEx", "long", 30^37, "int", 77)
[/autoit]
Hast du denn das Beispiel wirklich getestet bevor du es gepostet hast?
Ich kann deine Dll nicht testen da sich die DLL nicht entpacken lässt.
Oh sorry, liegt vllt an meinem 7zip, aber ja mein Beispiel ging.
DWORD hatte bei mir ausgereicht für die Zahl...
Ich uploade das zip mal eben nochmal..
€: Notfalls lass ich die Potenz per DLL berechnen, ist ja kein Problem 2 Zahlen zu übergeben.
€2: Beispiel + DLL im Anhang und Datentyp auf long long umgestellt.
€3:
ZitatSo oder so wäre die Dll aber nicht der begrenzende Faktor sondern wieder, wie am Anfang, AutoIt da du ja die Potenz erst von AutoIt berechnen lässt und dann das Ergebnis (was AutoIt nicht darstellen kann!) an die Dll übergibst:
Ich denke, dass AutoIt in diesem Fall, den Wert NICHT ausrechnet, sondern ihn einfach als 30^37 an die DLL übergibt.
€4: Verdammt nun hab ich die DLL neu gemacht aber das Beispiel nicht angepasst. Was mussi ch als Datentyp in AutoIt für long long angeben?
DWORD hatte bei mir ausgereicht für die Zahl...
Es ist Zufall dass dort 2 rauskommt als Ergebnis.
Die übergebenen Zahlen sind schon falsch also kann das Ergebnis gar nicht richtig werden.
Ich vermute es würde irgendein Wert mit 2,... rauskommen und durch die explizite Umwandlung in einen Integer wird dann daraus eine 2 was zufällig unserem gesuchten Ergebnis entspricht.
Teste mal dein Skript mit 30^37 % 76 - es müsste 68 herauskommen - mit deiner Dll aber 60.
€: Notfalls lass ich die Potenz per DLL berechnen, ist ja kein Problem 2 Zahlen zu übergeben.
In welchem Datentyp willst du das Ergebnis in C++ zwischenspeichern?
Lies dir den Link nochmal durch den ich gepostet habe und schau dir die Wertebereiche der Datentypen nochmal ganz genau an.
Ich denke, dass AutoIt in diesem Fall, den Wert NICHT ausrechnet, sondern ihn einfach als 30^37 an die DLL übergibt.
Welches Format soll das sein? - als String übergeben und die Dll weiß sofort wie man das auszuwerten hat?
AutoIt MUSS den Ausdruck vorher auswerten bevor es ihn übergibt.
Lass dir doch einfach die übergebene Zahl mal zum Test von der Dll direkt ausgeben.
Ich hätte es als BigInteger gespeichert, wobie man dann auch gleich die AutoIt Funktion nehmen könnte.
Ja okay vergesst meine DLL, da wollte man mal helfen ![]()
Na dann programmier doch die DLL entsprechend.
BigInteger-Bibliotheken sollte es ja einige geben.
Schneller als in AutoIt sollte das ganze ziemlich sicher werden.
Aber bitte nicht eingeschnappt sein weil wir deine dll hinterfragt haben.
Ich bin nicht eingeschnappt nur ein wenig enttäuscht, weil ich fange mit C++ grad erst an.
Aber gut, ich programmier ne DLL solange muss Aquaplant eben BigInt UDF nehmen.