Geteilt Rechnung vereinfachen in C

#5613343
Lesenswert?

Hallo

Ich habe eine Frage was eine vereinfachung des Codes heissen könnte.

Ich muss in meinem Programm 100000000/eine zahl rechnen. Dies 
funktioniert auch bestens. Jedoch wie ich weiss werden so viele 
rechenschritte benötigt um dies in meinem C code abzuarbeiten. Gibt es 
eine vereinfachte form wie schieben oder so. So währe dies ein wenig 
freundlicher vom code her.

Danke im voraus.
#5613430
Lesenswert?

Nutze einen ATmega2560 bei 16MHz. mit dem ICE Atmel compiler. Der 
divisor ist so im Datenblatt vorgegeben. So versuche ich das Programm 
nur zu optimieren. Mit dem compiler möchte ich eigentlich nicht 
arbeiten. Ist für mich nur eine halbe Lösung zu dem Problem und nicht 
das Problem aus der Welt geschaffen.
#5613432
Lesenswert?

Harry L. schrieb:
> Simon X. schrieb:
>> Den darf ich nicht einschalten, da es im Programm eine Stelle hat die
>> genau so durchgeführt werden muss wie sie steht.
>
> "broken by design"

Die Arbeit dem Compiler zu überlassen heisst für mich das man Faul ist 
und nicht. Aber verstehen ist was anderes. Es gibt tatsächlich stellen 
oder Rechenschritte die genau so erledigt werden müssen und nicht 
umgangen werden können.
Persönliche Seite #5613434
Lesenswert?

Simon X. schrieb:
> mit dem ICE Atmel compiler.

Das ist ein Debugger.

Simon X. schrieb:
> Der
> divisor ist so im Datenblatt vorgegeben.

Wenn Divisor (aus dem Datenblatt) und Dividend (100000000) fix sind, 
wird die Berechnung sowieso immer zu einer fixen Zahl vorberechnet.

Simon X. schrieb:
> Mit dem compiler möchte ich eigentlich nicht
> arbeiten.
Ohne Compiler kannst du auf dem AVR wohl kaum C nutzen. Was meinst du 
wirklich?

Simon X. schrieb:
> Ist für mich nur eine halbe Lösung zu dem Problem und nicht
> das Problem aus der Welt geschaffen.
Meinst du den Optimierer? Den darf man ruhig ordentlich ausnutzen, dafür 
ist der da. Ohne Optimierung zur kompilieren ist angezogene Handbremse.

Simon X. schrieb:
> Die Arbeit dem Compiler zu überlassen heisst für mich das man Faul ist
> und nicht.
Das heißt dass man kompakten, lesbaren und wartbaren Code schreibt und 
die Details dem Computer überlässt. Das ist ökonomisch. Wenn man 
unbedingt alles selber machen will, macht man es in Assembler. Übrigens 
beschleunigt der Optimizer selbst die besten C-Programme noch; ohne 
Optimierung baut der Compiler immer unnötige Dinge ein.

Simon X. schrieb:
> Es gibt tatsächlich stellen
> oder Rechenschritte die genau so erledigt werden müssen und nicht
> umgangen werden können.
Wenn sie korrekt formuliert sind, wird da auch nichts umgangen und das 
genau so gemacht wie gewünscht. Präzisiere das mal, was "genau so" 
erledigt werden soll und was der Optimierer da kaputt machen könnte.
#5613494
Lesenswert?

Simon X. schrieb:
> Den darf ich nicht einschalten, da es im Programm eine Stelle hat die
> genau so durchgeführt werden muss wie sie steht.

Kannst du uns bitte ein Beispiel geben, wo bei dir der Optimizer nicht 
aktiv werden darf?

Ansonsten kann man sehr bequem für Teile des Programms die Optimierung 
verbieten oder umschalten.

#pragma GCC push_options
#pragma GCC optimize ("O0")

hier dein kritischer Code

#pragma GCC pop_options
Gast #5613563
Lesenswert?

Simon X. schrieb:
> Jedoch wie ich weiss werden so viele
> rechenschritte benötigt um dies in meinem C code abzuarbeiten.
Wenn die 'eine Zahl' (der Divisor) eine Variable ist, dann weißt du es 
nicht.
Je nach dem welchen Wert die hat, werden daraus mehr oder weniger 
Operationen.

> Gibt es
> eine vereinfachte form wie schieben oder so. So währe dies ein wenig
> freundlicher vom code her.
Schieben geht einfach, wenn der Divisor eine Zweierpotenz ist.

Simon X. schrieb:
> Die Arbeit dem Compiler zu überlassen heisst für mich das man Faul ist
> und nicht.

Und nicht was?
Aber grundsätzlich: die Optimierung eines Programms kann der Compiler 
mit seinem Optimizer am besten. Das hat nichts mit Faulheit zu tun.
Gast #5613672
Lesenswert?

Simon X. schrieb:
> Den darf ich nicht einschalten, da es im Programm eine Stelle hat die
> genau so durchgeführt werden muss wie sie steht.
Interessant: Du haellst dich fuer besser und kompetenter als die 
Compilerbauer? Hut ab...

Simon X. schrieb:
> Es gibt tatsächlich stellen
> oder Rechenschritte die genau so erledigt werden müssen und nicht
> umgangen werden können.
Und du glaubst, das dein Programm das einzige auf dieser Welt ist, wo 
das der Fall ist, bzw. das alle anderen Entwickler auf der Welt fuer 
sowas die optimierung abschalten? Auch hier: Hut ab...

Simon X. schrieb:
> So versuche ich das Programm nur zu optimieren.
Genau hier faengt dein eigentliches Problem an:
Du haellst dich fuer besser und kompetenter als die Compilerbauer. Okay: 
Der Optimierer kann auch nicht zaubern, z.B. wenn der Code sehr schlecht 
ist.

Zeig doch bitte mal ein Stueckchen Code (compilierbar!) das dein Problem 
(also was die optimierung angeblich kaputt macht) fuer alle anderen hier 
im Forum nachvollziehbar zeigt.
Gast #5613696
Lesenswert?

Harry L. schrieb:

> Simon X. schrieb:
>> Den darf ich nicht einschalten, da es im Programm eine Stelle hat die
>> genau so durchgeführt werden muss wie sie steht.
>
> "broken by design"

Jau, aber anders als du denkst. Auch wenn es C nicht in den Kram passt, 
sind nunmal u.U. bestimmte Codeteile mit bestimmten Timing-Constraints 
zu bearbeiten, um das gewünschte Ergebnis zuverlässig zu erreichen. 
"broken by design" ist also hier: Verwendung einer ungeeigneten Sprache, 
nämlich einer die nur unvollkommene bis gar keine Kontrolle über die 
verbrauchte Rechenzeit ermöglicht.

Dass das meist nicht völlig dramatisch im Sinne einer kompletten 
Unbenutzbarkeit ist, liegt einfach nur daran, dass in sehr vielen Fällen 
"schnell genug" ausreichend ist. Das Problem ist aber auch hier: Man 
sollte eigentlich zumindest eine obere Grenze angeben können, bis zu der 
die Timing-Constraints eingehalten werden können...

Völlig unbrauchbar ist C allerdings prinzipiell für alles, wo es nicht 
genügt, schnell genug zu sein, sondern eine (ggf. innerhalb bestimmter 
Grenzen) exakte Laufzeit erforderlich ist.
Gast #5613736
Lesenswert?

Simon X. schrieb:
> Ich muss in meinem Programm 100000000/eine zahl rechnen. Dies
> funktioniert auch bestens. Jedoch wie ich weiss werden so viele
> rechenschritte benötigt um dies in meinem C code abzuarbeiten. Gibt es
> eine vereinfachte form wie schieben oder so. So währe dies ein wenig
> freundlicher vom code her.

Ohne irgendetwas über den Kontext und "eine zahl" zu wissen, wird das 
schwierig. Wenn es i.A. einfacher ginge, wäre die Division in der Praxis 
überflüssig. Du musst schon etwas mehr Information über dein 
eigentliches Problem rausrücken.
Falls "eine zahl" bspw. immer 0x00BEBC20 ist, würde sich die Operation 
fast in Luft auflösen.
#5613822
Lesenswert?

Simon X. schrieb:
> Ich muss in meinem Programm 100000000/eine zahl rechnen. Dies
> funktioniert auch bestens. Jedoch wie ich weiss werden so viele
> rechenschritte benötigt um dies in meinem C code abzuarbeiten. Gibt es
> eine vereinfachte form wie schieben oder so. So währe dies ein wenig
> freundlicher vom code her.

Es gibt für die Version "Variable"/" Konstante" die Umformung in 
"Variable"*"andere Konstante">>"noch eine andere Konstante".
Das ganze nennt sich Barrett-Verfahren und wird vom GCC in der Tat 
vollautomatisch eingesetzt, sobald Optimierungen aktiv sind und es der 
Wertebereich erlaubt.

Für deine Problematik, d.h. "Konstante"/"Variable" existiert meines 
Wissens nach kein derartiges verfahren.
#5614011
Lesenswert?

Peter D. schrieb:
> Solange das nicht feststeht, ist eine Optimierung überflüssig wie ein
> Kropf.

Unabhängig davon ist es aber auch recht sinnlos, den Compiler so 
einzustellen, dass er besonders ineffizienten Code produziert, um sich 
dann den Kopf darüber zu zerbrechen, wie man das von Hand wieder gerade 
biegen könnte.

Und dass …

Simon X. schrieb:
> es im Programm eine Stelle hat die genau so durchgeführt werden muss wie
> sie steht

… glaube ich nicht. So eine Aussage kommt eigentlich immer durch das 
fehlende Wissen, wie man es richtig macht.
Persönliche Seite #5614029
Lesenswert?

Ingo L. schrieb:
> Also der Optimizer/Compiler wird meines Wissens nicht etwas
> konstruieren, was andere Ergebnisse liefert als von dir per Code
> angestrebt.

Dazu muss der Code aber korrekt sein. Es gibt in C und C++ leider viele 
Möglichkeiten, (unbemerkt) fehlerhaften Code zu produzieren, welcher 
dann ggf. kaputt optimiert wird. Insbesondere bei Zugriffen auf 
Hardware-Register, bei denen Reihenfolge und Timing wichtig sind, bewegt 
man sich in einer Grauzone. Da aber IIRC die AVR hier relativ gutmütig 
sind sollten sich Lösungen finden lassen.
Es wäre praktisch, die fragliche Codestelle mal sehen zu können...
Moderator (Firma: Titel) Persönliche Seite #5614032
Lesenswert?

Simon X. schrieb:
> Es gibt tatsächlich stellen oder Rechenschritte die genau so erledigt
> werden müssen und nicht umgangen werden können.
Dann muss man die "Stellen" einfach so programmieren, dass sie immer 
das machen, was sie tun sollen. Mit Optimierung halt schneller...

Wenn ich Code habe, der ohne Optimierung läuft und mit Optimierung nicht 
mehr, dann weiß ich, dass der Code noch einen Fehler enthält.
#5614051
Lesenswert?

Ich glaube ich habe es verstanden. Der Fragesteller möchten bespasst 
werden. Irgendwas soll passieren, damit irgendwas anders wird. Kein 
Problem, dann machen wir das.

De actio juméntis insipiéntibus schlage ich eine Zerlegung in einen 
Kettenbruch vor. Das ist ein bisschen altmodisch (schon Euler hat ...) 
aber kann man mal machen. Die Mathematik ist ein bisschen aufwendiger, 
aber es gibt ein klassisches Lehrbuch online: 
https://archive.org/download/dielehrevondenk00perrgoog/dielehrevondenk00perrgoog.pdf
Gast #5614060
Lesenswert?

Hannes J. schrieb:
> Ich glaube ich habe es verstanden. Der Fragesteller möchten bespasst
> werden. Irgendwas soll passieren, damit irgendwas anders wird. Kein
> Problem, dann machen wir das.

Da warst Du jetzt schneller ;-)
Es geht um freundlichen Code! Vielleicht einen, der Beträge von der 
einen in eine andere Währung umrechnet.

Vielleicht gibt es auch noch eine Optimierung, die dafür sorgt, daß der 
µC nicht ca. 10000000 Befehle/s vergeudet.
Als Nächstes wird sicherlich stören, daß der Flash-Speicher nicht auf 
das letzte Byte gefüllt ist. Preisenkung vom Lieferanten?
Interessant, welche Probleme heutzutage in der Schule gelöst werden 
müssen.
Gast #5614739
Lesenswert?

S. R. schrieb:
> Division ist wiederholte Subtraktion, also kann man das auch so
> hinschreiben.

Angenommen, die fragliche Zahl wäre die 341256. Jetzt schreib mal die 
Aufgabe 100000000/341256(*) als Subtraktionen hin. Ich wüßte nicht, wie 
ich das anstellen soll. Aber wenn du das so einfach findest, schreib mal 
bitte auf, wie du das machen würdest.

(*) Die wirkliche Zahl wissen wir alle nicht, deshalb nur als Beispiel
#5614758
Lesenswert?

Hannes J. schrieb:
> Ich glaube ich habe es verstanden. Der Fragesteller möchten bespasst
> werden.

Das glaube ich mittlerweile auch! Und wenn man nicht weiss, wie groß die 
zweite Zahl sein wird, dann bleibt doch nur eine Float-Division. Auch 
wenn ich - wie gesagt- keine große Ahnung in "C" habe, so scheint es mir 
doch völlig unsinnig, in einer Hochsprache eine Rechenoperation "zu 
Fuss" selbst zu schreiben...
Und noch einmal meine Frage: der TO hat ein C-Programm, möchte aber 
keinen Compiler benutzen! Also was denn dann!!!
Gruß Rainer
Gast #5614788
Lesenswert?

Fritz B. schrieb:
> Angenommen, die fragliche Zahl wäre die 341256. Jetzt schreib mal die
> Aufgabe 100000000/341256(*) als Subtraktionen hin. Ich wüßte nicht, wie
> ich das anstellen soll. Aber wenn du das so einfach findest, schreib mal
> bitte auf, wie du das machen würdest.
1
int divisor = 100000000, quotient = 341256, result = 0;
2
divisor -= quotient / 2;
3
while(divisor > 0)
4
{
5
    divisor-=quotient;
6
    result++;
7
}
#5614801
Lesenswert?

Fritz B. schrieb:
> S. R. schrieb:
>> Division ist wiederholte Subtraktion, also kann man das auch so
>> hinschreiben.
>
> Angenommen, die fragliche Zahl wäre die 341256. Jetzt schreib mal die
> Aufgabe 100000000/341256(*) als Subtraktionen hin. Ich wüßte nicht, wie
> ich das anstellen soll. Aber wenn du das so einfach findest, schreib mal
> bitte auf, wie du das machen würdest.
Hast du im Fach Informatik in der Uni gepennt?
Das was jz23 da aufgeschrieben hat, ist eines der ersten Dinge die man 
lernt wwenn es darum geht ein wenig davon zu verstehen was unter der 
haube von Programmiersprachen geschieht :)
Gast #5614815
Lesenswert?

Fritz B. schrieb:
> Angenommen, die fragliche Zahl wäre die 341256. Jetzt schreib mal die
> Aufgabe 100000000/341256(*) als Subtraktionen hin. Ich wüßte nicht, wie
> ich das anstellen soll.

Dann hast du in der Schule wahrscheinlich die Unterrichtseinheit über 
schriftliche Division verpasst. Den ersten Kontakt mit der 
Vorgehensweise hättest du normalerweise im zweiten Halbjahr der 4ten 
Klasse haben sollen.
Gast #5614854
Lesenswert?

Niklas G. schrieb:
> Es gibt in C und C++ leider viele
> Möglichkeiten, (unbemerkt) fehlerhaften Code zu produzieren, welcher
> dann ggf. kaputt optimiert wird.
Wie kann denn kaputter Code noch kaputt optimiert werden? Der Code war 
schon vor der Optimierung kaputt, der Compiler und seine Optimierung 
machen den Fehler nur sichtbar. Sowas wie "ein bisschen schwanger" gibt 
es nicht. Entweder man ist es oder nicht.

Und das ist auch etwas was jedem klar sein muss wenn man mit C/C++ 
arbeitet:
Wenn man den Compiler mit Mist fuettert kann man nicht erwarten das 
Rosen dabei raus kommen.
#5615114
Lesenswert?

Leute, das ist nicht mehr wirklich witzig.
Ihr tut so als ob der TE aus Dummheit dieses Problem hätte und als ob 
ihr alle immer perfekten code schreiben würdet (und das vorallem schon 
seit eurer ersten Bekanntschaft mit einer Tastatur) >_>
Wart ihr nie in der Situation einmal sehr froh gewesen zu sein dass der 
code überhaupt lief. Egal wie?
Optimierungen auszuschalten ist da noch bei weitem das angenehmste.

Wenn ihr den TE nicht vollends verschreckt habt, beschreibt er aber 
vieleicht die betreffende code Stelle und man kann wieder was sinnvolles 
in diesen Thread schreiben.
#5615360
Lesenswert?

Peter D. schrieb:
> Es wurde immer noch nicht die Frage beantwortet, ob das Programm
> überhaupt zu langsam ist.

Und die 2. Frage ist, falls es zu langsam ist, ob dann überhaupt die 
Division der schuldige ist.

Ich hab da schon Sachen erlebt. Z.B. daß jemand für eine 
Multiplexanzeige jedesmal neu die Zahl komplett in Ziffern zerlegt, um 
dann davon ein Digit auszugeben.
Wer Rechnungen unnötig oft ausführt, darf sich nicht wundern, wenn dann 
wichtige Sachen zu langsam werden.
Persönliche Seite #5615370
Lesenswert?

Alex G. schrieb:
> Optimierungen auszuschalten ist da noch bei weitem das angenehmste.

Aber böse geschummelt. Es ist schon sinnvoll direkt zu lernen wie es 
richtig geht. Sonst gibt's bald ein böses Erwachen... Dazu kann man ja 
auch fragen wo genau das Problem liegt, wenn man es eingegrenzt hat.

Alex G. schrieb:
> Wenn ihr den TE nicht vollends verschreckt habt, beschreibt er aber
> vieleicht die betreffende code Stelle und man kann wieder was sinnvolles
> in diesen Thread schreiben.
Macht er ja leider nicht :-/
Gast #5615486
Lesenswert?

Alex G. schrieb:
> Hast du im Fach Informatik in der Uni gepennt?

Ich war weder an der Uni noch hab ich das Fach Informatik gehabt.
Es ist bemerkenswert, wie du darauf kommst, daß alle, die hier 
schreiben, an der Uni gewesen wären.
Aber trotzdem danke für die herablassende Beleidigung ;-)

@jz23: Ich danke dir.
Mit etwas nachdenken hätte ich selbst drauf kommen müssen...

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren