Das deutsche QBasic- und FreeBASIC-Forum Foren-Übersicht Das deutsche QBasic- und FreeBASIC-Forum
Für euch erreichbar unter qb-forum.de, fb-forum.de und freebasic-forum.de!
 
FAQFAQ   SuchenSuchen   MitgliederlisteMitgliederliste   BenutzergruppenBenutzergruppen  RegistrierenRegistrieren
ProfilProfil   Einloggen, um private Nachrichten zu lesenEinloggen, um private Nachrichten zu lesen   LoginLogin
Zur Begleitseite des Forums / Chat / Impressum
Aktueller Forenpartner:

MOD 8
Gehe zu Seite 1, 2  Weiter
 
Neues Thema eröffnen   Neue Antwort erstellen    Das deutsche QBasic- und FreeBASIC-Forum Foren-Übersicht -> Allgemeine Fragen zu FreeBASIC.
Vorheriges Thema anzeigen :: Nächstes Thema anzeigen  
Autor Nachricht
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 25.08.2020, 15:31    Titel: MOD 8 Antworten mit Zitat

Hallo, gibt es einen schnelleren Befehl, um MOD 8 zu bekommen ?

***
DIM AS USHORT N,A
DIM AS UINTEGER I
INPUT "N";N
PRINT TIMER
FOR I=1 TO 100000000
A= N MOD 8
NEXT I
PRINT TIMER
FOR I=1 TO 100000000
A=N SHL 13
A = A SHR 13
NEXT I
PRINT TIMER
SLEEP

***

Läuft auf dasselbe hinaus.

Gruß
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4594
Wohnort: ~/

BeitragVerfasst am: 25.08.2020, 16:17    Titel: Antworten mit Zitat

Bei Zweierpotenzen kannst du es noch mit "N AND 7" versuchen, das sollte schneller gehen als MOD - funktioniert aber nur mit Zweierpotenzen.

Laufen bei dir MOD und SHL/SHR wirklich gleich schnell? Bei mir war jetzt bei mehreren Versuchen die SHL/SHR-Methode fast doppelt so schnell (und auch etwas schneller als AND).
_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 25.08.2020, 16:43    Titel: Antworten mit Zitat

Ja, etwa gleich.

Hier mal für 1 MRD Interationen

N? 799
429666.4866057
429669.3533163
429672.2092275

Es betrifft nur die 8 speziell, da sie für ein Bitfeld mit UBYTE nötig ist

Danke !
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php


Zuletzt bearbeitet von pzktupel am 25.08.2020, 17:20, insgesamt einmal bearbeitet
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 25.08.2020, 17:08    Titel: Antworten mit Zitat

Ist ja geil mit N AND 7...bau ich gleich mal ins Sieb

Danke !

Nachtrag:

Also N AND 7 bringt keinerlei Speedvorteil gegenüber N MOD 8

System: Ryzen 1700
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php


Zuletzt bearbeitet von pzktupel am 26.08.2020, 09:23, insgesamt einmal bearbeitet
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4594
Wohnort: ~/

BeitragVerfasst am: 25.08.2020, 17:48    Titel: Antworten mit Zitat

Beispielausgabe bei mir:
Code:
N? 799
Start:     1072279.2778663
nach MOD:  1072279.5408398
nach SHL:  1072279.6632477
nach AND:  1072279.8420289


compiliert mit "-gen gas". Compiliert mit "-gen gcc" ist MOD etwas schneller, die beiden anderen Methoden deutlich langsamer. Sprich: Für eine Geschwindigkeitsoptimierung lohnt es sich wahrscheinlich, an den Compiler-Optionen zu schrauben.
(Insgesamt läuft gas bei mir etwas schneller, außer für MOD - und alles im Moment getestet in 32bit ("-gen gas" läuft ja auch nur unter 32bit ...))
_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 25.08.2020, 18:04    Titel: Antworten mit Zitat

habs mal mit -gen -gcc gemacht (ist mir komplett neu)

N? 5913
Start :434588.6120438
MOD :434591.4962621
SHL/SHR: 434594.4545164
AND 7 : 434597.2681629 *

2.8-2.9 s , etwa immer gleich. 1 Mrd Interationen
_____________

In der Tat ist -gcc gas unter 32bit ein Tick schneller im SHL/SHR als 64bit.
Problem ist aber wieder bei 32bit der begrenzte RAM
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php


Zuletzt bearbeitet von pzktupel am 25.08.2020, 18:14, insgesamt einmal bearbeitet
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4594
Wohnort: ~/

BeitragVerfasst am: 25.08.2020, 18:14    Titel: Antworten mit Zitat

Ich habe noch eine sehr verrückte Idee - läuft bei mir zwar auch nicht schneller, ist aber wenigstens schön verrückt. grinsen

Code:
TYPE TypBitfeld
  AS INTEGER mod8 : 3
END TYPE
DIM AS TypBitfeld bitfeld

FOR I=1 TO 100000000
  bitfeld.mod8 = N
  A = bitfeld.mod8
NEXT I

_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 25.08.2020, 18:30    Titel: Antworten mit Zitat

Außer Reichweite ist auch " VALUINT(BIN(N,3)) " für N MOD 8

Aber ingesamt, ist es leider nicht wirklich massiv schneller.

Wäre gut gewesen, wenn es einen Befehl gäbe, der die letzten 3 Bit von rechts sofort verwerten könnte.

Was mich auch etwas stört, ist das Freebasic für

DIM A(Bereich) AS UBYTE

A(N SHR 3)=BITSET(N SHR 3, N MOD 8) immer das Feld vorher wieder löscht.

Nur bei: A(N SHR 3)=BITSET(A(N SHR 3), N MOD 8 ) wird der Inhalt behalten und das BIT bei 0..7 ergänzt
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4594
Wohnort: ~/

BeitragVerfasst am: 25.08.2020, 18:41    Titel: Antworten mit Zitat

BITSET(N SHR 3, N MOD 8) setzt ein spezielles Bit im Ausdruck "N SHR 3" und nicht in der Variablen "A(N SHR 3)" - oder habe ich die Aussage falsch verstanden? "A(N SHR 3)" wird nicht vorher gelöscht, sondern mit dem Ergebnis von "BITSET(N SHR 3, N MOD 8)" überschrieben.
_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 25.08.2020, 18:56    Titel: Antworten mit Zitat

Speziell war es so gemeint.

Integerwert=100
Im Bitfeld F() also F(12)=00001000 wird das BIT gesetzt
jetzt ist der Integerwert=99
Im Bitfeld F() also F(12)=00000100 wird das BIT gesetzt

Wünschenswert wäre aber F(12)=00001100, das geht aber nur , wenn extra
F(12) im BITSET-Befehl eingebunden wird mit F(12)=BITSET(F(12),3)

Das Feld 12 umfasst alle Zahlen von 96 bis 103
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4594
Wohnort: ~/

BeitragVerfasst am: 25.08.2020, 19:03    Titel: Antworten mit Zitat

Zitat:
Wünschenswert wäre aber F(12)=00001100, das geht aber nur , wenn extra
F(12) im BITSET-Befehl eingebunden wird mit F(12)=BITSET(F(12),3)

Das halte ich für die einzig logische Möglichkeit. Die Funktion BITSET kann ja nicht wissen, welcher Variablen das Ganze dann zugewiesen wird (oder ob überhaupt). Eine andere denkbare Möglichkeit wäre wenn dann, wenn BITSET(F(12),3) gleich das Bit in F(12) setzen würde ohne Notwendigkeit einer nochmaligen Zuweisung.
_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 25.08.2020, 19:57    Titel: Antworten mit Zitat

F(12)=BITSET(F(12),3) ist die einzige Lösung.

Wenn man in einem Bereich siebt und in einem Bitfeld ablegt, dann ist es so, dass mehrmals über dieselbe Zahl drübergebügelt wird.

Bsp. 1001 würde durch die 7,11 und 13 erfasst werden.

1001 hat aber im Bitfeld -> F(125) mit Bitstelle 00000001
1003 hat F(125)=Bitstelle 00000100 , durch die 17 einmalig erfasst

Eigentlich würde es genügen, wenn es den Befehl als Einzelanweisung gäbe
wie
> BITSET(F(X SHR 3),X MOD 8) < , aber nein, der will noch ein "=" haben

Ist ein Bit gesetzt, dann setze halt nochmal und addiere nicht die numerischen werte, wie es auch vorkommt

Fazit:
Es ist unnötig in einem Feldinhalt ein Bit zu setzen und expliziet nochmal das Feld anzusprechen.


Sowas für eine volle Belegung für F(X SHR 3)

BITSET(F(X SHR 3),0)
BITSET(F(X SHR 3),1)
BITSET(F(X SHR 3),2)
BITSET(F(X SHR 3),3)
BITSET(F(X SHR 3),4)
BITSET(F(X SHR 3),5)
BITSET(F(X SHR 3),6)
BITSET(F(X SHR 3),7)

gibt es eben nicht,egal
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
hhr



Anmeldungsdatum: 15.07.2020
Beiträge: 84

BeitragVerfasst am: 25.08.2020, 20:10    Titel: Antworten mit Zitat

Ist so etwas gemeint?
Code:

Dim As Ubyte b

Print Bin(b)
b=b Or 8
Print Bin(b)
b=b Or 4
Print Bin(b)

b=0
Print Bin(b)
b=b Or 12
Print Bin(b)

Sleep

Mit der Oder-Funktion kann man gezielt Bits setzen.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 25.08.2020, 20:22    Titel: Antworten mit Zitat

Hallo !

Leider nicht wirklich.

Der Ursprung war , so schnell wie möglich von einer Zahl N das N MOD 8 zu berechnen, weil dieser Wert in einem Array das Bit auf 1 setzen soll.

Das zweite war, das ich es umständlich finde, wie man ein Bit schrittweise in einem Feldinhalt zwischen 0..7 ergänzen kann.

Ich habe ja die Lösung , aber denke FB könnte da noch Einsparungen teffen.

Setzt man ein Bit, geht die alte Position verloren.

Man könnte zwar 1 oder 0 an einer Stelle abfragen und bei 0 einfach addieren mit : F(x)+=, aber das kostet Zeit und ist damit unerwünscht.

Somit bleibt nur das genannte F(X SHR 3)=BITSET(F(X SHR 3), X MOD 8) übrig.

Das soll ja nun auch nicht ausufern, somit bleibt " MOD 8 " als Befehl nur übrig. [Oder gleichwertig "N AND 7"]
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4594
Wohnort: ~/

BeitragVerfasst am: 25.08.2020, 20:33    Titel: Antworten mit Zitat

Zitat:
Fazit:
Es ist unnötig in einem Feldinhalt ein Bit zu setzen und expliziet nochmal das Feld anzusprechen.

Naja, BITSET ist halt eine Funktion und keine Anweisung happy
Ich hätte vom Namen her auch erst vermutet, dass es so arbeitet wie du dachtest, aber BITSET verändert halt seine Parameter nicht (was in anderen Zusammenhängen auch wieder seine Vorteile hat).

Edit: Ich habe mal schnell nachgesehen, weil ich mich da zu erinnern glaubte ... und richtig, BITSET ist lediglich ein Macro:
Code:
#define Bitset( value, bit_number ) ((value) or (Cast(TypeOf(Value), 1) shl (bit_number)))

Von daher kann das auch nicht schneller werden als wenn du gleich diese Operatoren anwendest.
_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 25.08.2020, 22:53    Titel: Antworten mit Zitat

Aha, siehste und da gehen bei mir schon wieder die Lichter aus !

So tief gleich im Code rumwuseln kann ich eben doch nicht mit den Augen rollen
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
nemored



Anmeldungsdatum: 22.02.2007
Beiträge: 4594
Wohnort: ~/

BeitragVerfasst am: 25.08.2020, 23:34    Titel: Antworten mit Zitat

Ach was, im Code rumwuseln - das steht in der Referenz grinsen
_________________
Deine Chance beträgt 1:1000. Also musst du folgendes tun: Vergiss die 1000 und konzentriere dich auf die 1.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
volta



Anmeldungsdatum: 04.05.2005
Beiträge: 1874
Wohnort: D59192

BeitragVerfasst am: 26.08.2020, 01:19    Titel: Antworten mit Zitat

Hi,
N and 7 ist doch schon 5-6 mal schneller als N mod 8
Code:
Dim As UShort N=799, A
Dim As ULong I
Dim As Single t

t= Timer
For I=1 To 100000000
  A = N Mod 8
Next I
Print Timer-t

t= Timer
For I=1 To 100000000
  A = (N Shl 13) Shr 13
Next I
Print Timer-t

t= Timer
For I=1 To 100000000
  A = N And 7
Next I
Print Timer-t

t= Timer
For I=1 To 100000000
  Asm
    mov eax, [N]
    And eax, 7
    mov [A], eax
  End Asm
Next I
Print Timer-t

Sleep

_________________
Warnung an Choleriker:
Dieser Beitrag kann Spuren von Ironie & Sarkasmus enthalten.
Zu Risiken & Nebenwirkungen fragen Sie Ihren Therapeuten oder Psychiater.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden Website dieses Benutzers besuchen
pzktupel



Anmeldungsdatum: 07.07.2020
Beiträge: 81

BeitragVerfasst am: 26.08.2020, 06:29    Titel: Antworten mit Zitat

@volta

Den Assemblercode habe ich bei mir entfernt, da compilerfehler...aber hier für
10^9 Interationen nochmal die Zeiten mit Deinem Code

2.863855899951886
2.810774999961723
2.843578899977729

Es gewinnt klar sogar die SHL/SHR Methode, aber 0.04s ist auf 10^9 mal kein
Mehrgewinn

Da ist kein Unterschied,leider . Mit Freebasic 1.07 Win64 ändert sich auch nix.

Kann ja sein, dass alle Intel-PCs haben die wieder extra Befehlssätze haben.

Gruß
_________________
Umfangreichste Angaben zu Primzahl k-Tupel
https://www.pzktupel.de/ktuplets.php
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
volta



Anmeldungsdatum: 04.05.2005
Beiträge: 1874
Wohnort: D59192

BeitragVerfasst am: 26.08.2020, 08:37    Titel: Antworten mit Zitat

Hi,
ich hätte nicht gedacht das die 32Bit Version mit N mod 8 so langsam ist.
Da FB sehr maschinennah compiliert sind die asm Teile nur unwesentlich schneller.
Ich hatte die falsche Registergrößen benutzt (in 32Bit ist das kein Problem).
Code:
Dim As UShort N=799, A
Dim As ULong I
Dim As Single t

t= Timer
For I=1 To 1000000000
  A = N Mod 8
Next I
Print Timer-t

t= Timer
For I=1 To 1000000000
  A = N Shl 13
  A = A Shr 13
Next I
Print Timer-t

t= Timer
For I=1 To 1000000000
  Asm
    mov ax, [N]
    Shl ax, 13
    Shr ax, 13
    mov [A], ax
  End Asm
Next I
Print Timer-t

t= Timer
For I=1 To 1000000000
  A = N And 7
Next I
Print Timer-t

t= Timer
For I=1 To 1000000000
  Asm
    mov ax, [N]
    And ax, 7
    mov [A], ax
  End Asm
Next I
Print Timer-t

Sleep

_________________
Warnung an Choleriker:
Dieser Beitrag kann Spuren von Ironie & Sarkasmus enthalten.
Zu Risiken & Nebenwirkungen fragen Sie Ihren Therapeuten oder Psychiater.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden Website dieses Benutzers besuchen
Beiträge der letzten Zeit anzeigen:   
Neues Thema eröffnen   Neue Antwort erstellen    Das deutsche QBasic- und FreeBASIC-Forum Foren-Übersicht -> Allgemeine Fragen zu FreeBASIC. Alle Zeiten sind GMT + 1 Stunde
Gehe zu Seite 1, 2  Weiter
Seite 1 von 2

 
Gehe zu:  
Du kannst keine Beiträge in dieses Forum schreiben.
Du kannst auf Beiträge in diesem Forum nicht antworten.
Du kannst deine Beiträge in diesem Forum nicht bearbeiten.
Du kannst deine Beiträge in diesem Forum nicht löschen.
Du kannst an Umfragen in diesem Forum nicht mitmachen.

 Impressum :: Datenschutz