// mittakal.cpp /* Ohjelma muuttaa kartalta mitattuja matkoja luontoon. Vesa Lappalainen 8.4.1997 Muutokset 10.4.1997 + vertaa-metodi + Kerroin - saantimetodi + muutamia rivinvaihtoja ja mittakaavan lasku oikeaksi Muutokset 10.4.1997 luennolla + k„ytt„j„yst„v„llisyytt„ (ei tarvitse sy”tt„„ mittakaavaa aina) + lukee tiedostoa yksikot.dat, joka on suraavaa muotoa: mm 1.0 cm 10.0 dm 100.0 m 1000.0 km 1000000.0 inch 25.4 + tietorakenne linkityksi listaksi ilman yst„v„luokkaa Muutokset 11.4.1997 + cMuunnos::alusta muutettu int-typpiseksi + cMuunnokset::lue my”s int-tyyppiseksi 1:10000 10 cm => 1000*1000 * 10 1:20 200 kyyn„r„„ Luokat ja vastuut: cNaytto - kysella ja tulostaa cMuunnos - tietaa mika jono muuttuu miksi kertoimeksi - cMuunnokset - etsi„ oikea kerroin Piirr„ t„h„n tietorakenteen kuva */ #include #include #include #include #include //---------------------------------------------------------------------------- class cMuunnos { string yks; double ker; cMuunnos *seur; public: cMuunnos(const char *aYks="",double aKerroin=0.0) : yks(aYks), ker(aKerroin) { seur = NULL; } int alusta(const char *s) { // palauttaa 1 jos onnistuu hyvin char cyks[80]; int lkm = sscanf(s,"%s %lf",cyks,&ker); if ( lkm > 0 ) yks = cyks; return lkm==2; } double Kerroin() const { return ker; } int vertaa(const char *vyks) const { return strcmp(yks.c_str(),vyks); } int operator==(const char *vyks) { return (vertaa(vyks) == 0); } void linkita(cMuunnos *uSeur) { seur = uSeur; } cMuunnos *Seuraava() { return seur; } }; /* int operator==(const cMuunnos &yks, const char *vyks) { return ( yks.vertaa(vyks) == 0 ); } */ //---------------------------------------------------------------------------- class cMuunnokset { int maxkoko; // pois... int lkm; cMuunnos *eka; cMuunnos *vika; public: cMuunnokset(int aKoko) { lkm = 0; maxkoko = aKoko; eka = NULL; vika = NULL; } ~cMuunnokset(); int lisaa(const cMuunnos &uusi) { cMuunnos *muun; muun = new cMuunnos(uusi); // 1. luodaan kopio if ( muun == NULL ) return 1; lkm++; if ( eka == NULL ) // 2a. jos tyhj„ lista eka = muun; else vika->linkita(muun); // 2b. uusi vanhan viim. seur vika = muun; // 3. uudesta uusi viim. muun->linkita(NULL); // 4. viim. viimeiseksi return 0; } double kerroin(const char *yks); int lue(const char *nimi); }; cMuunnokset::~cMuunnokset() { cMuunnos *seur, *p = eka; while ( p != NULL ) { seur = p->Seuraava(); delete p; p = seur; } lkm = 0; eka = NULL; vika = NULL; } int cMuunnokset::lue(const char *nimi) { ifstream fi(nimi); if ( !fi ) return 0; char s[80]; cMuunnos uusi; while ( 1 ) { fi.getline(s,sizeof(s)); if ( !fi ) break; if ( uusi.alusta(s) ) lisaa(uusi); } return lkm; } double cMuunnokset::kerroin(const char *yks) { cMuunnos *p; for ( p = eka; p != NULL; p = p->Seuraava() ) if ( *p == yks ) return p->Kerroin(); return 0; // Makuasia! } //---------------------------------------------------------------------------- class cNaytto { cMuunnokset *muunnokset; public: cNaytto(cMuunnokset *aMuun) { muunnokset = aMuun; } int kysele(); }; int cNaytto::kysele() { string jono; double mittakaava=200000.0,matka,matka_km,matka_mm; char yksikko[80]="mm"; // Huono kohta!!! while ( 1 ) { cout << "Mittakaava ja matka >"; getline(cin,jono,'\n'); if ( jono == "loppu" ) return 0; if ( jono == "" ) return 0; if ( strchr(jono.c_str(),':') != NULL ) sscanf(jono.c_str(),"1:%lf %lf %s",&mittakaava,&matka,yksikko); else sscanf(jono.c_str(),"%lf %s",&matka,yksikko); matka_mm = matka * muunnokset->kerroin(yksikko); matka_km = matka_mm * mittakaava / (1000.0*1000.0) ; cout << "Matka maastossa on " << matka_km << " km" << endl; } } int main(void) { cMuunnokset muunnokset(10); if ( muunnokset.lue("yksikot.dat") <= 0 ) { cout << "Ei l”ydy tiedostoa yksikot.dat" << endl; return 1; } cNaytto naytto(&muunnokset); naytto.kysele(); return 0; }