cin.get çok ilginç çalışıyor

Başlatan exclipit, 23 Ağustos 2013 - 23:05:17

« önceki - sonraki »

0 Üyeler ve 1 Ziyaretçi konuyu incelemekte.

exclipit

Ben basit bir kod yazıp derliyorum. Burada, kuzeye, güneye, doğuya ve batıya hareket oluyor ve bu koordinat sistemindeki x ve değerlerine atanıyor. Fakat conio.h dosyasını kullanamadığım için cin.get ile tuşları alayım diyorum, normal cin gibi çalışıyor bu fonksiyon da. Enterleyince giriyor, ve programın çıktısı çok ilginç, koordinatları iki kez yazıyor...


#include <iostream>
using namespace std;

int main(){
cout << "Program burada basliyor." << endl;
int x = 0;
int y = 0;
char tus = 'a';
cout << "Kuzey: k" << endl << "Guney: g" << endl << "Dogu: d" << endl << "Bati: b" << endl;
cout << "Cikis tusu: o" << endl << endl;

while (tus != 'o'){
tus = cin.get();
switch(tus){
case 'k': y--; break;
case 'g': y++; break;
case 'd': x++; break;
case 'b': x--; break;
}

cout << "x: " << x << "y: " << y << endl;
}
return 0;
}


Çıktılar:

Program burada basliyor.
Kuzey: k
Guney: g
Dogu: d
Bati: b
Cikis tusu: o

k
x: 0y: -1
x: 0y: -1
k
x: 0y: -2
x: 0y: -2
k
x: 0y: -3
x: 0y: -3
d
x: 1y: -3
x: 1y: -3
o
x: 1y: -3


Acaba yukarıda dikkatsizliğimden kaynaklanan bir şeyler mi var? Çünkü gerçekten hala anlamadım... Orada koordinatları iki kez yazmaması lazım. Ya da ikinci yazışından önce, bir kez daha cin.get ile veri alıp koordinatları ayarlaması lazım...
Çalışan iki el, dua eden binlerce elden daha çok iş yapar. – Gene Roddenberry

alorak

while mantığında sıkıntı var. while zaten default durumu karşılıyor. tuş değerini while'ın dışına çıkartıp daha sonra while yaparsan sorun çözülür. ama while'ı da default seçmende bir programlama hatası var zaten. ama asıl sorunun cevabı tuş değerini alma işlemi while içinde olması.

Örneğin şöyle yapmalısın:

tus = cin.get();
while (tus != 'o'){

switch(tus){
case 'k': y--; break;
case 'g': y++; break;
case 'd': x++; break;
case 'b': x--; break;

}
tus = cin.get();
cout << "x: " << x << "y: " << y << endl;
cout << y;
}
özgürlük için

exclipit

Ben Robert Lafore'nin "Nesne Yönelimli C++ Programlama Kılavuzu"ndan şu örneği vereyim. Anlamadığım yerler olmalı sanırım. Yoksa bu döngünün içerisinde tuş alma işlemi bir tek cin.get'e mi özgü? :/ Orada aynen şöyle bir programcık var:


// adelseif.cpp
// macera programi ile ELSE...IF yapisi
#include <iostream>
using namespace std;
#include <conio.h>          // getche() icin

int main()
    {
    char dir='a';
    int x=10, y=10;
   
    cout << "Type Enter to quit\n";
    while ( dir != '\r' )           //Enter girilene kadar
        {
        cout << "\nYour location is " << x << ", " << y;
        cout << "\nPress direction key (n,s,e,w): ";
        dir = getche();     //karakteri al
        if( dir == 'n' )    //kuzeye git
            y--;
        else if( dir=='s' ) //guneye git
            y++;
        else if( dir=='e' ) //doguya git
            x++;
        else if( dir=='w' ) // batiya git
            x--;
        }   //while'in sonu
    }   //main'in sonu


Conio.h olmadığı için, ben de cin.get() kullanıyorum kendi programımda. Bu program sadece Windows'ta çalışır...
Çalışan iki el, dua eden binlerce elden daha çok iş yapar. – Gene Roddenberry

alorak

Normal cin fonksiyonunu kullandığınızda sorun olmuyor. Deminki dediğim tam doğru değilmiş.

   while (tus != 'o'){
   cin>>tus;
   switch(tus){
   case 'k': y--; break;
   case 'g': y++; break;
   case 'd': x++; break;
   case 'b': x--; break;
   }
   cout << "x: " << x << "y: " << y << endl;
   }
Ayrıca while içerisinde o fonksiyonu kullandığımızda while bittiğinde tekrar fonksiyonu çağırmakta.
özgürlük için

exclipit

Sence g++ derleyicisinden kaynaklı bir şey olabilir mi?
Çalışan iki el, dua eden binlerce elden daha çok iş yapar. – Gene Roddenberry

alorak

Alıntı yapılan: exclipit - 24 Ağustos 2013 - 00:15:48
Sence g++ derleyicisinden kaynaklı bir şey olabilir mi?

Windowsta başka bir derleyiciyle deneme şansınız varsa bunu görebiliriz. Düşünceniz doğru olabileceği gibi .get() fonksiyonunun da bir özelliği olabilir tam bilemiyorum.
özgürlük için

sem

case ifadesine default ekleyerek sorunu daha net görebilirsiniz... get() fonskyionu enter'ı da alınıyor gibi görünüyor... Bu durumda uygulama şu şekilde çalışıyor gibi;

tus = cin.get();           /// Bu aşamada kullanıcıdan bilgi bekleniyor ve kullanıcı tarafından tampona yazılan bilgi;   "k\n"   ---> bir tane k ve bir de enter karakteri girilmiş olsun.
case 'k': y--; break;    /// y değeri bir eksiltildi ve ekrana yazıldı çünkü burada tus değişkeni k değerinde.
cout << "x: " << x << "y: " << y << endl;  /// burada değerler ekrana basıldı.


While döngüsü tekrarlamalı;

tus = cin.get();           /// Bu aşamada kullanıcıdan bilgi bekleniyor, çünkü get() metodunun okuyabileceği değer var; bir önceki iterasyonda k değeri alınmıştı tampondan,                                             /// ama tamponda "\n" karakteri hala duruyor.

case:                            /// x ya da y değeri değişmemeli çünkü tus = "\n" durumda. Bu nedenle hiç case ifadesine girilmemeli.

cout << "x: " << x << "y: " << y << endl;  /// Bir önceki değerler olduğu gibi ekrana basılmalı. Çünkü değerlerde değişiklik olmadı.



while döngüsü tekrarlamalı;


tus = cin.get(); // kullanıcıdan bilgi bekleniyor çünkü tampon boş.... Kullanıcı yine bilgi girmeli.


Hatta benzeri sorunu çözmüştük diye anımsıyorum forumda.

Çözüm;

* While döngüsünde tus değeri == "\n" continue uygulanabilir.
* stdin tamponu her bir karakter okumasundan sonra boşaltılabilir.

-> stdin (standart input) tamponunun boşaltılması için çok eskilerden bir başlık.;

http://forum.ubuntu-tr.net/index.php?topic=17803.msg215154#msg215154


Mesaj tekrarı yüzünden mesajınız birleştirildi. Bu mesajın gönderim tarihi : 24 Ağustos 2013 - 15:23:28

NOT: metin editöründeki yazarken ki hali ile foruma gönderdiğim ile birbiri ile uyumlu olmadığı için sıkıntılı görünüyor iletim. Kusura bakmayın.
".NET çemberinden geçen lirisist etkisi bir 'Volcano', bir yüzüm Java bir yüzüm Badalamenti Don Tano"
----------------------------------------------------------------------------------------------------------------------
"Her yer ölüm yine, burası dünya
Derken ölüm bile bu nasıl dünya?
Benden ölüm dile, batıyor gün yine
Burası dünya?

WhiteScars

cin.get demeden önce cin.ignore yazmayı denermisin?

Input streaminde karakterler kalıyor olabilir. cin ignore ile buffer'ı flush edip alabilirsin. Yazdığın koda çok dikkatli bakmadım ama bir dene istersen.
İnsanoğluna bırakabileceğiniz en güzel miras tecrübelerinizdir.