Herzlich Willkommen, lieber Gast!
  Sie befinden sich hier:

  Forum » Rätselecke » 20. Virtualrästel (anfänger - Fortgeschrittene)

Forum | Hilfe | Team | Links | Impressum | > Suche < | Mitglieder | Registrieren | Einloggen
  Quicklinks: MSDN-Online || STL || clib Reference Grundlagen || Literatur || E-Books || Zubehör || > F.A.Q. < || Downloads   

Autor Thread - Seiten: > 1 < [ 2 ] [ 3 ] [ 4 ]
000
30.04.2003, 15:16 Uhr
virtual
Sexiest Bit alive
(Operator)


Zu schreiben ist ein Programm, welches die Schnittmenge zweier Mengen berechnet. Dabei sollen die Elemente der beiden Mengen der Einfachheit halber Buchtaben sein. Der Benutzer gibt zum Andang des Programms die Mächtigkeit der Mengen ein (aka Anzahl der Elemente). Das Programm bestimmt dann per Zufall die Elemente dieser Mengen und gibt sowohl den Inhalt dieser Mengen als auch die Schnittmenge aus.
Exemplarische Ausgabe:

C++:
Mächtigkeit Menge 1: 3
Mächtigkeit Menge 2: 4
Menge 1: { a, g, x }
Menge 2: { f, g, w, z }
Schnittmenge: { g }


Folgende Hints:
1. Typisch für Mengen im mathematischen Sinne ist, daß jedes Element nur einmal vorkommen darf, dh eine Menge darf nicht zweimal den gleichen Buchstaben enthalten
2. Die Klasse std::set aus der STL implemtiert bereits eine Menge, ist jedoch kein Muß, diese zu verwenden.
3. Aus der in (1) genannten Beschränkung ergibt sich, daß nicht jede Mächtigkeit erlaubt ist.
4. Wie man mit Zufall umgeht, wird zb hier erklärt.

Der Gewinner erhält einen feucht-warmen Händedruck.
Der Rechtsweg ist ausgeschlossen.
--
Gruß, virtual
Quote of the Month
Ich eß' nur was ein Gesicht hat (Creme 21)

Dieser Post wurde am 30.04.2003 um 16:22 Uhr von virtual editiert.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
001
30.04.2003, 16:10 Uhr
~0xdeadbeef
Gast


Die Mächtigkeit der ersten Menge ist auch 4, wenn mich nicht alles täuscht.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
002
30.04.2003, 16:22 Uhr
virtual
Sexiest Bit alive
(Operator)


Danke
--
Gruß, virtual
Quote of the Month
Ich eß' nur was ein Gesicht hat (Creme 21)
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
003
30.04.2003, 17:04 Uhr
Windalf
Der wo fast so viele Posts wie FloSoft...
(Operator)


bevor beefy wieder seine high-end-template-Lösung postet schick ich mal das hier


C++:
#include <stdlib.h>
#include <stdio.h>

int irand( int a, int e){
    double r = e - a + 1;
    return a + (int)(r * rand()/(RAND_MAX+1.0));
}



int main(int argc, char* argv[]){

int i,j,anzahl1,anzahl2;
char menge1[26],menge2[26],schnittmenge[26], vereinigungsmenge[26];

printf("Mächtigkeit Menge1(max26): "); scanf("%d",&anzahl1);
printf("Mächtigkeit Menge2(max26): "); scanf("%d",&anzahl2);


for(i=0;i<26;i++){
    menge1[i]=0;
    menge2[i]=0;
    schnittmenge[i]=0;
    vereinigungsmenge[i]=0;

}


for(i=0;i<anzahl1;i++){

    j=irand(65,65+25);
    while(menge1[j-65]!=0)j=irand(65,65+25);
    menge1[j-65]=j;
    
}

for(i=0;i<anzahl2;i++){

    j=irand(65,65+25);
    while(menge2[j-65]!=0)j=irand(65,65+25);
    menge2[j-65]=j;
    
}

for(i=0;i<26;i++){
    
    if( (menge1[i]!=0) && (menge1[i]==menge2[i]) ) schnittmenge[i]=menge1[i];
    if      (menge1[i]!=0) vereinigungsmenge[i]=menge1[i];
    else if (menge2[i]!=0) vereinigungsmenge[i]=menge2[i];

}

    
printf("\nMenge 1:\n");
for(i=0;i<26;i++) printf("%c",menge1[i]);
printf("\n\nMenge 2:\n");
for(i=0;i<26;i++) printf("%c",menge2[i]);
printf("\n\nSchnitt:\n");
for(i=0;i<26;i++) printf("%c",schnittmenge[i]);
printf("\n\nVereinigung:\n");
for(i=0;i<26;i++) printf("%c",vereinigungsmenge[i]);
printf("\n\n");

    
return 0;
}


--
...fleißig wie zwei Weißbrote
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
004
30.04.2003, 19:36 Uhr
~0xdeadbeef
Gast


Na, mit Fakultät ist da nicht viel zu machen, weil die Mengen nicht zur Compilezeit feststehen. Wie dem auch sei, ich würds so machen:

C++:
#include <set>
#include <iostream>
#include <algorithm>
#include <iterator>
#include <sys/time.h>

using namespace std;

int main(int argc, char *argv[]) {
    set<char> my_sets[2], out_set;
  
    srand(time(0));

    for(int i = 0; i < 2; ++i) {
        int m;
        cout << "Mächtigkeit der Menge " << (i+1) << " eingeben: ";
        cin >> m;
        for(int j = 0; j < m; ++j) {
            char c;
            do {
                c = 'a' + (rand() % 26);
            } while(my_sets[i].find(c) != my_sets[i].end());
            my_sets[i].insert(c);
        }
    }

    set_intersection(my_sets[0].begin(), my_sets[0].end(),
                                    my_sets[1].begin(), my_sets[1].end(),
                                    inserter(out_set, out_set.begin()));

    for(int i = 0; i < 2; ++i) {
        cout << "Menge " << (i+1) << ": ";
        copy(my_sets[i].begin(), my_sets[i].end(), ostream_iterator<char>(cout, " "));
        cout << endl;
    }
    cout << "Schnittmenge: ";
    copy(out_set.begin(), out_set.end(), ostream_iterator<char>(cout, " "));
    cout << endl;

    return 0;
}


Das ist jetzt natürlich ohne Bouncechecks bei der Eingabe, aber das überlasse ich euch als untergeordnete Übungsaufgabe
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
005
01.05.2003, 20:00 Uhr
~0xdeadbeef
Gast


Kleines Update: Wenns nur um die Ausgabe geht, kann man das ganze natürlich auch effizienter gestalten:

C++:
#include <set>
#include <iostream>
#include <algorithm>
#include <iterator>
#include <sys/time.h>

using namespace std;

int main(int argc, char *argv[]) {
  set<char> my_sets[2];

  srand(time(0));

  for(int i = 0; i < 2; ++i) {
    int m = 0;
    cout << "Mächtigkeit der Menge " << (i+1) << " eingeben (1 - 26): " << flush;
    cin >> m;

    for(int j = 0; j < m; ++j) {
      char c;
      do {
        c = 'a' + (rand() % 26);
      } while(my_sets[i].find(c) != my_sets[i].end());
      my_sets[i].insert(c);
    }
  }

  for(int i = 0; i < 2; ++i) {
    cout << "Menge " << (i+1) << ": ";
    copy(my_sets[i].begin(), my_sets[i].end(), ostream_iterator<char>(cout, " "));
    cout << endl;
  }
  cout << "Schnittmenge: ";
  set_intersection(my_sets[0].begin(), my_sets[0].end(),
                   my_sets[1].begin(), my_sets[1].end(),
                   ostream_iterator<char>(cout, " "));
  cout << endl;

  return 0;
}

 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
006
02.05.2003, 08:43 Uhr
virtual
Sexiest Bit alive
(Operator)


Das ist so meine Lösung. Bin rel. nah an Beefies Lösung dran, nur mit dem Zufalls und der Ausgabe handle ich es anders :

C++:
#include <iostream>
#include <algorithm>
#include <set>
#include <cstdlib>

void beautified_output(std::set<char>& s)
{
    std::set<char>::const_iterator i = s.begin();
    std::set<char>::const_iterator end = s.end();

    std::cout<<'{';
    if (i!=end) std::cout<<*i++;
    while (i!=end) std::cout<<", "<<*i++;
    std::cout<<'}';
}


int main()
{
    char elements[] = "abcdefghijklmnopqrstuvwxyz";
    srand(time(NULL));

    // 1. Menge bestimmen
    int m1;
    std::cout<<"Mächtigkeit Menge 1: "<<std::flush;
    std::cin>>m1;
    std::random_shuffle(elements, elements+26);
    std::set<char> s1(elements, elements+std::min(26,m1));

    // 2. Menge bestimmen
    int m2;
    std::cout<<"Mächtigkeit Menge 2: "<<std::flush;
    std::cin>>m2;
    std::random_shuffle(elements, elements+26);
    std::set<char> s2(elements, elements+std::min(26,m2));

    // Schnittmenge bestimmen
    std::set<char> is;
    std::set_intersection(s1.begin(), s1.end(),
                          s2.begin(), s2.end(),
                          std::inserter(is, is.begin()));

    // Ausgabe
    std::cout<<"Menge 1:      "; beautified_output(s1); std::cout<<std::endl;
    std::cout<<"Menge 2:      "; beautified_output(s2); std::cout<<std::endl;
    std::cout<<"Schnittmenge: "; beautified_output(is); std::cout<<std::endl;  

}


--
Gruß, virtual
Quote of the Month
Ich eß' nur was ein Gesicht hat (Creme 21)
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
007
02.05.2003, 09:38 Uhr
~christian
Gast


Hi Virtual!

Warum verwendest du denn das std::flush?
Ich dachte, und ich hoffe ich täusche mich jetzt nicht, dass flush nur bewirkt, dass der Ausgabepuffer sofort geleert wird und am Ausgabegerät angezeigt wird.
Aber nachdem doch cin und cout standardmäßig tied sind sollte das doch eh egal sein, oder? Also solange du nicht cout und dann scanf verwendest.

Grüße, Christian
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
008
02.05.2003, 10:05 Uhr
virtual
Sexiest Bit alive
(Operator)


@christian
Mit dem Tied hast Du recht, ich habs mir aber angewöhnt aus folgenden Gründen:
1. Ich arbeite auch ganz gerne mal mit Streams, die nicht getied sind. Meine Lösung brintt die korrekte Ausgabe, unabh. davon, ob getied wurde oder nicht.
2. Man kann komische Effekte bekommen, wenn man cout und/oder cerr redirected hat.
3. Ich mache (für mich, nicht für das Programm) deutlich, daß eine loisch zusammenhängende Ausgabe beendet ist.
--
Gruß, virtual
Quote of the Month
Ich eß' nur was ein Gesicht hat (Creme 21)
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
009
02.05.2003, 12:06 Uhr
~Heiko
Gast


@beefy und virtual
was haltet ihr denn von meiner Lösung. Ist die schlecht? Wenn ja an welchen Stellen und warum?

Danke Heiko
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
Seiten: > 1 < [ 2 ] [ 3 ] [ 4 ]     [ Rätselecke ]  


ThWBoard 2.73 FloSoft-Edition
© by Paul Baecher & Felix Gonschorek (www.thwboard.de)

Anpassungen des Forums
© by Flo-Soft (www.flo-soft.de)

Sie sind Besucher: