2009-06-16 22 views
7

मैंने "The C Programming Language" (के & आर) पढ़ना शुरू कर दिया है और मुझे getchar() फ़ंक्शन के बारे में संदेह है।'getchar() `उपयोगकर्ता इनपुट कहां स्टोर करता है?

उदाहरण के लिए इस कोड:

#include <stdio.h> 

main() 
{ 
    int c; 

    c = getchar(); 
    putchar(c); 
    printf("\n"); 
} 

टाइप toomanychars + CTRL + डी (EOF) प्रिंट सिर्फ t। मुझे लगता है कि इसकी उम्मीद है क्योंकि यह पहला चरित्र पेश किया गया है।

लेकिन तब कोड के इस अन्य टुकड़ा:

#include <stdio.h> 

main() 
{ 
    int c; 

    while((c = getchar()) != EOF) 
    putchar(c); 
} 

टाइप toomanychars + CTRL + डी (EOF) toomanychars प्रिंट करता है।

मेरा सवाल यह है कि, ऐसा क्यों होता है यदि मेरे पास केवल एक चर चर हो? शेष वर्ण संग्रहित कहां हैं?

संपादित करें:

जवाब के लिए हर किसी के लिए धन्यवाद, मैं अब ... केवल एक ही पकड़ इसे पाने के लिए शुरू:

पहला कार्यक्रम बाहर निकलता है जब दिया CTRL + डी जबकि दूसरा पूरा स्ट्रिंग प्रिंट करता है और फिर अधिक उपयोगकर्ता इनपुट की प्रतीक्षा करता है। यह एक और स्ट्रिंग के लिए क्यों इंतजार करता है और पहले की तरह बाहर नहीं निकलता है?

+1

आपका दूसरा दृष्टिकोण सिर्फ EOF जब तक लूप। CTRL + D (विशिष्ट यूनिक्स सिस्टम पर) EOF में परिणाम नहीं होगा जब तक कि आप अपनी खुद की एक लाइन पर यह मारा। Ctrl + डी के बाद आप एक चरित्र लिखा है EOF – nos

उत्तर

4

यह फ़ाइल की तरह इनपुट स्ट्रीम का इलाज कर रहा है। ऐसा लगता है जैसे आपने "toomanychars" टेक्स्ट वाली एक फ़ाइल खोली और इसे एक समय में एक वर्ण को पढ़ या आउटपुट किया।

पहले उदाहरण में, थोड़ी देर के लूप की अनुपस्थिति में, ऐसा लगता है जैसे आपने एक फ़ाइल खोली और पहले अक्षर को पढ़ा, और उसके बाद इसे आउटपुट किया। हालांकि दूसरा उदाहरण वर्णों को तब तक पढ़ना जारी रखेगा जब तक कि यह फ़ाइल सिग्नल (ctrl+D आपके मामले में) का अंत हो जाता है जैसे कि यह डिस्क पर फ़ाइल से पढ़ रहा था।


आपके अपडेट किए गए प्रश्न के उत्तर में, आप किस ऑपरेटिंग सिस्टम का उपयोग कर रहे हैं? मैंने इसे अपने विंडोज एक्सपी लैपटॉप पर चलाया और यह ठीक काम किया। अगर मैं एंटर दबाता हूं, तो यह मेरे द्वारा अब तक की गई प्रिंट को प्रिंट करेगा, एक नई लाइन बनाएं, और फिर जारी रखें। (getchar() फ़ंक्शन तब तक वापस नहीं आता जब तक आप एंटर दबाते हैं, तब जब इनपुट बफर में कुछ भी नहीं कहा जाता है)। जब मैं CTRL+Z (विंडोज़ में ईओएफ) दबाता हूं, तो प्रोग्राम समाप्त हो जाता है। ध्यान दें कि विंडोज़ में, ईओएफ कमांड प्रॉम्प्ट में ईओएफ के रूप में गिनने के लिए स्वयं की एक पंक्ति पर होना चाहिए। मुझे नहीं पता कि यह व्यवहार लिनक्स में नकल किया गया है, या जो भी सिस्टम आप चल रहे हैं।

+0

@Carson में परिणाम नहीं करता है, वास्तव में! ईओएफ अपनी लाइन में होना चाहिए। आपका बहुत बहुत धन्यवाद! –

+0

आपका स्वागत है। मैं यह भी साथ संघर्ष किया लेकिन हल यह धन्यवाद अतः :) –

9

getchar मानक इनपुट से एक ही चरित्र प्राप्त करता है, जो इस मामले में कीबोर्ड बफर है।

दूसरे उदाहरण में, getchar समारोह एक while पाश जो जारी है जब तक यह एक EOF मुठभेड़ों में है, इसलिए यह पाशन रखना होगा और एक चरित्र को पुनः प्राप्त (और स्क्रीन के चरित्र प्रिंट) जब तक इनपुट खाली हो जाता है।

getchar पर लगातार कॉल इनपुट से आने वाले लगातार वर्ण प्राप्त करेंगे।

ओह, और इस सवाल के लिए बुरा महसूस न करें - जब मुझे पहली बार इस मुद्दे का सामना करना पड़ा तो मुझे परेशान था।

+0

यह पाशन सही होने के बाद यह 'जबकि (ग = getchar())' बयान का सामना करना पड़ता है, या उसे दबाना होगा पाश दर्ज करें और फिर के लिए यह इंतजार करता है शुरू होता है के लिए? मैं क्या देख सकते हैं, यह 'जबकि()' पाश के बाद ही हम एंटर दबाएं के शरीर पर अमल करता है। मेरा प्रश्न है: 'getchar()' 'जब तक enter' या' Ctrl + D' (अपने सिस्टम पर) दबाया जाता है 'जबकि()' पाश प्रतीक्षा करने के लिए और क्या बस के बाद की ओर लौटने से 'जबकि() 'लूप और फिर शेष शरीर को निष्पादित करना। – dud3

3

आपका पहला कार्यक्रम केवल एक चरित्र पढ़ता है, इसे प्रिंट करता है, और बाहर निकलता है। आपके दूसरे कार्यक्रम में लूप है। यह एक समय में वर्णों को पढ़ता रहता है और उन्हें तब तक प्रिंट करता है जब तक यह एक ईओएफ चरित्र नहीं पढ़ता। किसी भी समय केवल एक वर्ण संग्रहीत किया जाता है।

2

आप एक ही समय में प्रत्येक चरित्र को रखने के लिए केवल c का उपयोग कर रहे हैं।

एक बार जब आप पहले चार (t) putchar(c) का उपयोग कर प्रदर्शित किया है, तो आप चर c के बगल में चरित्र (o) बताए, पिछले मान (t) की जगह c के मूल्य के बारे में भूल जाओ।

1

कोड आप इस संस्करण को समझने के लिए आसान लग सकता है कार्यात्मक

main(){ 
    int c; 
    c = getchar(); 
    while(c != EOF) { 
    putchar(c); 
    c = getchar(); 
    } 
} 

के बराबर है। सशर्त में असाइनमेंट डालने का एकमात्र कारण है कि 'c = getchar()' को दो बार टाइप करने से बचें।

4

कुछ यहाँ buffered है। जैसे stdout FILE * जो पुचर लिखता है लाइन हो सकता है। buffered। जब प्रोग्राम समाप्त होता है (या एक नई लाइन का सामना करता है) ऐसी फ़ाइल * fflush() 'ed होगी और आप आउटपुट देखेंगे।

कुछ मामलों में आप जो वास्तविक टर्मिनल देख रहे हैं, वह आउटपुट को एक नई लाइन तक बफर कर सकता है, या जब तक कि टर्मिनल को अपने बफर को फ्लश करने का निर्देश नहीं दिया जाता है, जो तब हो सकता है जब वर्तमान अग्रभूमि प्रोग्राम ईमानी से बाहर निकलता है एक नया संकेत

अब, वास्तविक मामला क्या होने की संभावना है, यह है कि यह इनपुट है जो buffered (आउटपुट के अलावा :-)) है जब आप चाबियाँ दबाते हैं तो यह आपकी टर्मिनल विंडो पर दिखाई देगा। हालांकि टर्मिनल उन पात्रों को आपके एप्लिकेशन पर नहीं भेजेगा, यह तब तक बफर करेगा जब तक कि आप इसे Ctrl + D के साथ अंत में इनपुट करने के लिए निर्देशित न करें, और संभवतः एक नई लाइन भी।

int main() { 
    int c; 
    while((c = getchar()) != EOF) { 
    if(c != '\n') 
     putchar(c); 
    } 
    return 0; 
} 

अपने कार्यक्रम एक वाक्य खिला की कोशिश करें, और Enter दबाएं: यहाँ के आसपास खेलते हैं और विचार के बारे में करने के लिए एक और संस्करण है। और अगर आप पर टिप्पणी करते हैं तो ऐसा ही करें यदि (सी! = '\ N') हो सकता है कि आप यह निर्धारित कर सकें कि आपका इनपुट, आउटपुट या दोनों किसी तरह से बफर किए गए हैं या नहीं। यदि आप उपरोक्त को चलाते हैं तो यह अधिक दिलचस्प हो जाता है: ./mytest | ./mytest

(साइडकॉममेंट के रूप में, ध्यान दें कि सीटीआरडी + डी एक चरित्र नहीं है, न ही यह ईओएफ है। लेकिन कुछ प्रणालियों पर यह इनपुट स्ट्रीम बंद कर देगा जो फिर से पढ़ने के लिए प्रयास करने वाले किसी भी व्यक्ति को ईओएफ बढ़ाएगा धारा।)

0

आपके अद्यतन प्रश्न के लिए, पहले उदाहरण में, केवल एक वर्ण पढ़ा जाता है। यह कभी भी ईओएफ तक नहीं पहुंचता है। कार्यक्रम समाप्त हो जाता है क्योंकि printf निर्देश को पूरा करने के बाद ऐसा करने के लिए कुछ भी नहीं है। यह सिर्फ एक चरित्र पढ़ता है। इसे प्रिंट करता है। एक नई लाइन में डालता है। और फिर समाप्त हो जाता है क्योंकि इसमें कुछ और करने के लिए कुछ नहीं है। यह एक से अधिक चरित्र नहीं पढ़ता है।

जबकि दूसरे कोड में, गचर और पुचर थोड़ी देर के अंदर मौजूद हैं।इसमें, कार्यक्रम ईओएफ चरित्र (^ डी) तक पहुंचने तक वर्णों को एक-एक करके पढ़ता रहता है (जैसा कि इसे लूप द्वारा ऐसा करने के लिए किया जाता है)। उस बिंदु पर, यह सी! = ईओएफ से मेल खाता है और चूंकि स्थितियां संतुष्ट नहीं हैं, यह लूप से बाहर आती है। अब निष्पादित करने के लिए कोई और कथन नहीं है। तो कार्यक्रम इस बिंदु पर समाप्त हो जाता है।

उम्मीद है कि इससे मदद मिलती है।

संबंधित मुद्दे