capajera18 Temat założony przez niniejszego użytkownika |
ponownie potrzebuje pomocy - zabezpieczenie przed wpisaniem znaku » 2011-05-04 12:36:39 Witam serdecznie, mam ponownie problem z zabezpieczeniem przed wpisaniem znaku otórz #include <iostream> #include <conio.h>
using namespace std;
int main() { long double liczba, liczba2, wynik; long long menu; bool sprawdz = cin.good(); bool spr = cin.good(); while( 1 ) { cout << "\n\n\n\n\t\t\t *** KALKULATOR by CAPAJERA_18 ***" << endl; cout << "Dodawanie [1] " << endl; cout << "odejmowanie [2] " << endl; cout << "dzielenie [3] " << endl; cout << "mnozenie [4] " << endl; cout << "Wyjscie z programu [0] " << endl; cout << "\n\nWYBIERZ OPCJE I NACISNIJ ENTER -> "; cin >> menu; cin.clear(); cin.sync(); switch( menu ) { do { case 1: cout << "\n\n -> Jako A i B podaj 0 by zakonczyc dodawanie <- \n\n" << endl; do { cout << "podaj liczbe A "; cin >> liczba; cin.clear(); cin.sync(); sprawdz = cin.good(); cout << "\npodaj liczbe B "; cin >> liczba2; cin.clear(); cin.sync(); sprawdz = cin.good(); if( sprawdz == false ) do { cout << "\nLiczbe, nie literke: "; cin >> liczba; cin.clear(); cin.sync(); sprawdz = cin.good(); cout << "\nJeszcze raz: "; cin >> liczba2; cin.clear(); cin.sync(); sprawdz = cin.good(); } while( !sprawdz ); wynik = liczba + liczba2; cout << "\n\t\t\t " << liczba << " + " << liczba2 << " = " << wynik << endl; } while( liczba != 0 || liczba2 != 0 ); cout << " *** EXIT *** " << endl; break; case 2: cout << "\n\n -> Jako A i B podaj 0 aby zakonczyc odejmowanie <- \n\n" << endl; do { cout << "\npodaj liczbe A "; cin >> liczba; cin.clear(); cin.sync(); spr = cin.good(); cout << "\npodaj liczbe B "; cin >> liczba2; cin.clear(); cin.sync(); spr = cin.good(); if( spr == false ) do { cout << "\nLiczbe, nie literke: "; cin >> liczba; cin.clear(); cin.sync(); spr = cin.good(); cout << "\nJeszcze raz: "; cin >> liczba2; cin.clear(); cin.sync(); spr = cin.good(); } while( !spr ); wynik = liczba - liczba2; cout << "\n\t\t\t " << liczba << " - " << liczba2 << " = " << wynik << endl; } while( liczba != 0 || liczba2 != 0 ); cout << " *** EXIT *** " << endl; break;
Przedstawiam fragment kalkulatora mojego autorstwa, (No prawie mojego - pomoc Pana Elano92), mianowicie problem polega na tym że zabezpieczenie przed wpisaniem znaku typu A-Z lub !@#! itp. itd. działa tylko i wyłącznie w -dodawaniu- lecz w odejmowaniu to samo zabezpieczenie już nie działa tak samo w dzieleniu i mnożeniu po wpisaniu znaku zwraca mi dziwne wartości typu -1.#IND - -1.#IND = -1.#IND
I pytanie do Was , czym to może być spowodowane ? Kolejne jak mogę poprawić to zabezpieczenie tak by działało w innych obliczeniach ? Kurcze... jak mogę napisać własne zabezpieczenie za pomocą if() ? Myśle już długo nad tym i naprawde kombinuje i nic a wiadomo dopiero zaczynam Naprawde prosze o pomoc |
|
ison |
» 2011-05-04 12:52:28 Problem leży w tym, że sprawdzasz jedynie drugą liczbę czy została wczytana niepoprawnie cout << "podaj liczbe A "; cin >> liczba; cin.clear(); cin.sync(); sprawdz = cin.good(); cout << "\npodaj liczbe B "; cin >> liczba2; cin.clear(); cin.sync(); sprawdz = cin.good();
if( sprawdz == false )
Skorzystaj z 2 osobnych zmiennych cout << "podaj liczbe A "; cin >> liczba; cin.clear(); cin.sync(); sprawdz1 = cin.good(); cout << "\npodaj liczbe B "; cin >> liczba2; cin.clear(); cin.sync(); sprawdz2 = cin.good();
if( sprawdz1 == false || sprawdz2 == false )
|
|
capajera18 Temat założony przez niniejszego użytkownika |
» 2011-05-04 12:56:36 OK spróbuje zaraz dam odpowiedz jak poszło
Chce Pan Coffe Panie Ison ? |
|
dmx81 |
» 2011-05-04 13:01:40 pisze z komorki wiec odp nie bedzie wylewna,ale pomysl o innej konstrukcji zabezpieczenia,ja bym to zrobil sprawdz = false; whlie( !sprawdz ) { cout << "wpisz liczbe"; cin >> liczba; if( cin.good() ) sprawdz = true; else { cin.clear(); cin.sync(); a to zamknij w petli dla kazdej z liczb...i pokombinuj tez nad konstrukcja switcha,aby nie bylo kodu pomiedzy case,bo zmniejsza to czytelnosc i prowadzi do nieoczekiwanych zachowan(o ile nie jest to zamierzone) a mowie tu o tym,ze przed case dajesz do/while itd
Ps...zanim skonczylem odp juz sie inne pojawily,nie ma to jak komorka;p |
|
capajera18 Temat założony przez niniejszego użytkownika |
» 2011-05-04 13:10:05 OK pokombinuje |
|
capajera18 Temat założony przez niniejszego użytkownika |
» 2011-05-04 13:15:16 Daję odpowiedz dla Pana ison, niestety tym razem nawet w dodawaniu zabezpieczenie nie działa :-) . zwraca tą dziwną wartośc
-1.#IND - ....
A co sądzicie o takim rozwiązaniu ?? Tj ze strony 4programmers.net int zmienna; while( !( cin >> zmienna ) ) { cin.clear(); cin.sync(); }
|
|
ison |
» 2011-05-04 13:26:33 Teraz dopiero zauważyłem, cin.good() powinno być wywoływane przed czyszczeniem bufora/flag ;) Trochę skrócony kod: #include <iostream> #include <conio.h>
using namespace std;
int main() { long double liczba, liczba2, wynik; long long menu; bool sprawdz1; bool sprawdz2; bool spr = cin.good(); while( 1 ) { cout << "\n\n\n\n\t\t\t *** KALKULATOR by CAPAJERA_18 ***" << endl; cout << "Dodawanie [1] " << endl; cout << "odejmowanie [2] " << endl; cout << "dzielenie [3] " << endl; cout << "mnozenie [4] " << endl; cout << "Wyjscie z programu [0] " << endl; cout << "\n\nWYBIERZ OPCJE I NACISNIJ ENTER -> "; cin >> menu; cin.clear(); cin.sync(); switch( menu ) { case 1: cout << "\n\n -> Jako A i B podaj 0 by zakonczyc dodawanie <- \n\n" << endl; do { cout << "podaj liczbe A "; cin >> liczba; sprawdz1 = cin.good(); cin.clear(); cin.sync(); cout << "\npodaj liczbe B "; cin >> liczba2; sprawdz2 = cin.good(); cin.clear(); cin.sync(); if( sprawdz1 == false || sprawdz2 == false ) do { cout << "\nLiczbe, nie literke: "; cin >> liczba; sprawdz1 = cin.good(); cin.clear(); cin.sync(); cout << "\nJeszcze raz: "; cin >> liczba2; sprawdz2 = cin.good(); cin.clear(); cin.sync(); } while( !sprawdz1 || !sprawdz2 ); wynik = liczba + liczba2; cout << "\n\t\t\t " << liczba << " + " << liczba2 << " = " << wynik << endl; } while( liczba != 0 || liczba2 != 0 ); } } }
już raczej działa OK, jedyna wada jest taka, że jeśli jako pierwszą liczbę poda się literkę to program poprosi i tak o następną a komunikat mówiący o złym wprowadzeniu danych zostanie wyświetlony dopiero po wprowadzeniu drugiej liczby, nie wiem czy tak miało być ale ja bym to zrobił trochę inaczej :) Możesz sobie stworzyć funkcję, która będzie czytała wartość do tej pory aż ją poprawnie wczyta. void WczytajLiczbe( std::string komunikat, long double & liczba ) { cout << komunikat; do { cin.clear(); cin.sync(); cin >> liczba; if( cin.good() ) break; cout << "Wprowadzono zla wartosc\n"; } while( 1 ); }
wtedy zamiast pisać cout << "podaj liczbe A "; cin >> liczba; sprawdz1 = cin.good(); cin.clear(); cin.sync(); cout << "\npodaj liczbe B "; cin >> liczba2; sprawdz2 = cin.good(); cin.clear(); cin.sync();
if( sprawdz1 == false || sprawdz2 == false ) do { cout << "\nLiczbe, nie literke: "; cin >> liczba; sprawdz1 = cin.good(); cin.clear(); cin.sync(); cout << "\nJeszcze raz: "; cin >> liczba2; sprawdz2 = cin.good(); cin.clear(); cin.sync(); } while( !sprawdz1 || !sprawdz2 );
można zwyczajnie użyć fukncji WczytajLiczbe( "Podaj liczbe A\n", liczba ); WczytajLiczbe( "Podaj liczbe B\n", liczba2 );
prawda, że krócej? |
|
capajera18 Temat założony przez niniejszego użytkownika |
» 2011-05-04 13:46:15 No tak wszystko jest fajnie :) Dzieki, tylko że teraz jak podałem w pętli while( liczba != 0 || liczba2 != 0 );
to nie chce mi wyjść przykładowo z odejmowania czy dodawania do głównego menu, Poprostu podaje
*** EXIT ***
I dalej nic się z programem nie dzieje :-) Edit; OK moj błąd którego sie doszukałem :-) |
|
« 1 » 2 |