ist ein fehler in diesem programm?
-
Natürlich kann man nicht immer stur nach dem Standard programmieren. Man muss dann halt für die einzelnen Compiler workarounds bauen alá:
#ifdef __MSVC7 ... #endif
-
Firebyte::Username schrieb:
@Michael E.
Kannst du mal das Primzahlprogramm posten, wie es nach deiner Syntax aussähe?
#include <iostream> using namespace std; int main() { for(int i = 2; i < 100; ++i) { bool isPrime = true; for(int j = 2; j <= i/2; ++j) { if(i % j == 0) isPrime = false; } if(isPrime == true) cout << i << " ist eine Primzahl.\n"; } return 0; }Wieso willst du das wissen?
-
Firebyte::Username schrieb:
Natürlich kann man nicht immer stur nach dem Standard programmieren. Man muss dann halt für die einzelnen Compiler workarounds bauen alá:
#ifdef __MSVC7 ... #endifAlso programmierst du für Compiler...
-
Michael E. schrieb:
Firebyte::Username schrieb:
@Michael E.
Kannst du mal das Primzahlprogramm posten, wie es nach deiner Syntax aussähe?
#include <iostream> using namespace std; int main() { for(int i = 2; i < 100; ++i) { bool isPrime = true; for(int j = 2; j <= i/2; ++j) { if(i % j == 0) isPrime = false; } if(isPrime == true) cout << i << " ist eine Primzahl.\n"; } return 0; }Wieso willst du das wissen?
Da hätte ich auch nichts gegen, aber in dem Buch sind die Variablen am Anfang, außerde sind dort keine Leerzeichen zwischen Operatoren, und du hast ja jetzt selber ne Klammer bei dem Zweiten for benutzt! So säh das im Buchstyle aus:
#include <iostream> using namespace std; int main() { int i, j; bool isPrime; for(i=2;i<100;++i) { bool isPrime = true; for(j=2; j<=i/2;++j) if(i % j == 0) isPrime = false; if(isPrime == true) cout<<i<<" ist eine Primzahl.\n"; } return 0; }
-
Und?
-
ich bedanke mich für die zahlreichen antworten.
aber noch ne frage:
was ist VC6.0?und übrigens ich habe schon öfters fehler in diesem buch gefunden!!
obwohl es auf der seite nicht als fehlerhalt und zugleich als schlecht eingestuft wird
hier der link:
http://www.c-plusplus.net/cms/modules.php?op=modload&name=mbBooks&file=index&func=isbn&isbn=3826609808ben1990
-
-
#include <iostream> using namespace std; bool isprime(int n) { int sqrt_n=static_cast<int>(sqrt(double(n))); for (int i=2; i<=sqrt_n; ++i) if (!(n%i)) return false; return true; } int main() { static const int bis=10; for (int i=2; i<bis; ++i) if (isprime(i)) cout << i << endl; }... oder das ganze als Metaprogramm ...
#include <iostream> template <int n, int a, int b, bool eq=a==b> struct isprime_helper; /** * @brief Ermittelt ob Zahl eine Primzahl ist (Brute-Force-Methode) * @param n Der zu testende Wert */ template <int n> struct isprime { /** * Zahle bis max=sqrt(n) testen. Für sqrt(n)<2 gilt max=2 */ static const int sqrt_n = static_cast<int>(sqrt(n)); static const int max = sqrt_n<2 ? 2 : sqrt_n; static const bool value=isprime_helper<n, 2, 2>::value; }; struct isprime<1> { static const bool value=false; }; template <int n, int a, int b> struct isprime_helper<n, a, b, false> { static const bool value=(n%a==0) ? false : isprime_helper<n, a+1, b>::value;}; template <int n, int a, int b> struct isprime_helper<n, a, b, true> { static const bool value=(n%a==0) ? false : true; }; int main() { std::cout << isprime<5>::value << std::endl; std::cout << isprime<100>::value << std::endl; }
-
lucky_tux schrieb:
#include <iostream> using namespace std; bool isprime(int n) { int sqrt_n=static_cast<int>(sqrt(double(n))); for (int i=2; i<=sqrt_n; ++i) if (!(n%i)) return false; return true; } int main() { static const int bis=10; for (int i=2; i<bis; ++i) if (isprime(i)) cout << i << endl; }... oder das ganze als Metaprogramm ...
#include <iostream> template <int n, int a, int b, bool eq=a==b> struct isprime_helper; /** * @brief Ermittelt ob Zahl eine Primzahl ist (Brute-Force-Methode) * @param n Der zu testende Wert */ template <int n> struct isprime { /** * Zahle bis max=sqrt(n) testen. Für sqrt(n)<2 gilt max=2 */ static const int sqrt_n = static_cast<int>(sqrt(n)); static const int max = sqrt_n<2 ? 2 : sqrt_n; static const bool value=isprime_helper<n, 2, 2>::value; }; struct isprime<1> { static const bool value=false; }; template <int n, int a, int b> struct isprime_helper<n, a, b, false> { static const bool value=(n%a==0) ? false : isprime_helper<n, a+1, b>::value;}; template <int n, int a, int b> struct isprime_helper<n, a, b, true> { static const bool value=(n%a==0) ? false : true; }; int main() { std::cout << isprime<5>::value << std::endl; std::cout << isprime<100>::value << std::endl; }Hast du toll gemacht......aber glaubst du dass das Ben1990 irgendwie weiter bringt?
-
@lucky_tux
Ich bekomme beim Meta-Programm folgende Meldung:
main9.cpp:17: error: a function call cannot appear in a constant-expression
bei der Zeile mit sqrt(). Muss ich was an meinem Compiler einstellen oder woran leigt das?mfg.
-
Ich wage zu behaupten dass das Metaprogramm nicht funktioniert, weil das Metaprogramm nicht vollständig instanziiert werden kann. Denn der sqrt-Aufruf kann zur Compilezeit einfach nicht konstant ausgewertet werden.
-
ja! erste geposteten funktion ist ein wenig modifiziert. Es wird nur der Rest aller Zahlen bis \|n (Wurzel n), für n gleich zu testender wert, getestet. Bei einer Vielzahl an Werten kann dadurch so mach eine Sekunde eingespart werden.
Bei der zweiten Variante weiß ich nicht ob es ihm weiterhilft. Aber vlt. hilft es jemand anderem weiter. Die Zeiteinsparung spricht jedenfalls (meiner Meinung nach) für sich! In dem zweiten Beispiel wird nämlich die komplette Berechnung ob es sich um eine Zufallszahl handelt zu Zeiten des Kompilierens ausgeführt
-
Bei mir funktioniert alles. Die einzige Fehlermeldung die ich bekomme ist folgende

main.cpp:42:1: Warnung: Kein Newline am Dateiende
Wie rufst du die Metafunktion auf? Natürlich lässt sich die Metafunktion nur mit einem konstanten ausdruck aufrufen, also nicht mit einer Laufvariablen einer Schleife.
-
lucky_tux schrieb:
Bei mir funktioniert alles. Die einzige Fehlermeldung die ich bekomme ist folgende

main.cpp:42:1: Warnung: Kein Newline am Dateiende
Wie rufst du die Metafunktion auf? Natürlich lässt sich die Metafunktion nur mit einem konstanten ausdruck aufrufen, also nicht mit einer Laufvariablen einer Schleife.
Wenn ich einfach nur deinen Beispiel-Code compilieren will, tritt das Problem auf. Ich hab gcc 3.4.4.
mfg.
-
#include <iostream> template <bool Val, typename True, typename False> struct if_ : public True { }; template <typename True, typename False> struct if_<false, True, False> : public False { }; template <bool Val> struct BoolType { static const bool value = Val; }; template <unsigned int N, int i, bool Val> struct isprime_helper : public if_<(i*i > N) , BoolType<true> , if_<(N % i) , isprime_helper<N, i + 1, Val> , BoolType<false> > > {}; template <unsigned int N> struct isprime { static const bool value = isprime_helper<N, 2, false>::value; }; template<> struct isprime<1> { static const bool value = false; }; int main() { std::cout << isprime<5>::value << std::endl; std::cout << isprime<100>::value << std::endl; }So funktionierts.
Spacelord schrieb:
Hast du toll gemacht......aber glaubst du dass das Ben1990 irgendwie weiter bringt?
Dann passt es doch sehr gut zum Rest des Threads

-
lucky_tux schrieb:
... oder das ganze als Metaprogramm ...
Hm...
ich weiss nicht, ich weiss nicht:Statt den Standard zu zitieren zitiere ich zur Abwechslung mal Comeau C++:
"ComeauTest.c", line 17: error: identifier "sqrt" is undefined static const int sqrt_n = static_cast<int>(sqrt(n)); ^ "ComeauTest.c", line 17: error: function call is not allowed in a constant expression static const int sqrt_n = static_cast<int>(sqrt(n)); ^ "ComeauTest.c", line 23: error: specializing class "isprime<1>" without "template<>" syntax is nonstandard struct isprime<1> ^Viel mehr muss man dazu nicht sagen.

-
#include <iostream> using namespace std; int main() { cout << "2 ist eine Primzahl\n"; cout << "3 ist eine Primzahl\n"; cout << "5 ist eine Primzahl\n"; // ... }Die Geschwindigkeit spricht für sich

-
template <unsigned int N, int i, bool Val> struct isprime_helper : public if_<(i*i > N) , BoolType<true> , if_<(N % i) , isprime_helper<N, i + 1, Val> , BoolType<false> > > {};Sehr geschickt gelöst das Problem mit sqrt. Wenigstens einer der die Funktionalität der Metaprogrammierung nicht grundlos unterschätzt.
@Antiposer:
Ich finde es schade, dass sich so wenige Leute mit der Metaprogrammierung auseinandersetzen. Vorallendingen Anfänger sind von dem neuen, noch recht unerforschten (Bezug auf Libraries wie die MPL) Konzepten der Metaprogrammierung abgeschreckt. Vorallendingen in wissenschaftlichen Applikationen würde ich diese Art der Programmierung nie unterschätzen. Die MPL z.B. etliche Möglichkeiten für mathematische Berechnungen, Type Traits und Manipulation, uvm.
-
lucky_tux schrieb:
Vorallendingen Anfänger sind von dem neuen, noch recht unerforschten (Bezug auf Libraries wie die MPL) Konzepten der Metaprogrammierung abgeschreckt.
Ich denk eher, dass die Syntax und die Programmlogik noch zu schwer für nen Anfänger sind.
-
lucky_tux schrieb:
@Antiposer:
Ich finde es schade, dass sich so wenige Leute mit der Metaprogrammierung auseinandersetzen. Vorallendingen Anfänger sind von dem neuen, noch recht unerforschten (Bezug auf Libraries wie die MPL) Konzepten der Metaprogrammierung abgeschreckt. Vorallendingen in wissenschaftlichen Applikationen würde ich diese Art der Programmierung nie unterschätzen. Die MPL z.B. etliche Möglichkeiten für mathematische Berechnungen, Type Traits und Manipulation, uvm.Keine Frage, da hast Du die Intention meines Kommentares auch total misverstanden. In der Tat kann man damit feine Sachen machen, aber zwei Dinge sollte man nicht vergessen: Es ist deutlich komplizierter es richtig zu machen (wie schön gezeigt wurde) und daher nicht einsteigerfreundlich (und verwirrt den Fragesteller unter Garantie mehr als es ihm hilft) und es reduziert die Portabilität, da Metaprogrammierung halt schwerer auf verschiedene Plattformen portiert werden kann. Im speziellen Fall der Primzahlenbestimmung geht zudem die Anzahl der Situationen, in denen man zur Compilezeit den Primzahlentest machen kann (weil man da den zu testenden Wert schon kennt), grob gegen Null.
Metaprogrammierung hat viele Vorteile, aber auch manche Nachteile, und wer beruflich in grossen Projekten zu tun hat wird als einen starken Nachteil die langen Übersetzungszeiten empfinden, die nicht unerwähnt bleiben sollten. Ich kenne aus leidiger beruflicher Erfahung genug Projekte die man an einem Tag kaum oder garnicht mehr bauen kann, bei grösserflächigerem Metaprogrammierungs-Einsatz würde diese Zeit noch deutlich schlimmer. Ein echter Kostenfaktor. Wenn die Primzahl aber wirklich statisch getestet werden müsste, könnte man das immernoch in die Initialisierungsphase der Anwendung ziehen und sich das Ergebnis merken, wäre genauso Flott zur eigentlichen Laufzeit, nicht wirklich gross im Code und schnellst zu übersetzen.
So bleibt ein von Dir möglicherweise als Aufruf zur Würdigung von Metaprogrammierung gedachtes Posting halt erstmal als wenig hilfreich und zudem falsch bezogen auf das Topic (das nicht nach geschickter Primzahlenerzeugung fragt, sondern nach Fehlern in einem konkreten Listing aus einem Buch) der schale Geschmack eines möglichen Poser-Postings. Wenn ich das wirklich missverstanden habe, so tut mir das leid. Aber speziell nach der Antwort der Art "bei mir tut es aber" musste ich einfach davon ausgehen, weil das kein Argument für konformen Code ist und das sollte man wissen, wenn man mit Metaprogammierung erfolgreich arbeiten will.

Also nix für ungut, ich mag Metaprogrammierung auch!
