फ़ाइल डिस्क्रिप्टर और फ़ाइल पॉइंटर के बीच क्या अंतर है?


114

मैं फ़ाइल डिस्क्रिप्टर और फ़ाइल पॉइंटर के बीच अंतर जानना चाहता हूं।

इसके अलावा, आप किस परिदृश्य में एक के बजाय दूसरे का उपयोग करेंगे?


जवाबों:


144

एक फाइल डिस्क्रिप्टर एक निम्न-स्तरीय पूर्णांक "हैंडल" है, जिसका उपयोग लिनक्स या अन्य यूनिक्स जैसी प्रणालियों में, कर्नेल स्तर पर एक खुली हुई फ़ाइल (या सॉकेट, या जो कुछ भी) की पहचान करने के लिए किया जाता है।

आप इस तरह के रूप में वास्तविक यूनिक्स कॉल, करने के लिए "नग्न" फ़ाइल वर्णनकर्ता पारित read(), write()और इतने पर।

एक FILEसूचक एक सी मानक पुस्तकालय स्तर के निर्माण, एक फ़ाइल का प्रतिनिधित्व करते थे है। FILEफ़ाइल वर्णनकर्ता लपेटता है, और बफरिंग और अन्य सुविधाओं कहते हैं मैं / हे आसान बनाने के लिए।

उत्तीर्ण होने FILEजैसे मानक सी कार्यों के लिए संकेत दिए गए fread()और fwrite()


@nvl: fildes निश्चित रूप से विंडोज़ के लिए उपलब्ध है, जैसे msdn.microsoft.com/en-us/library/z0kc8e3z%28VS.80%29.aspx
kennytm

2
@unwind क्या आप "नग्न" फ़ाइल वर्णनकर्ताओं द्वारा मतलब है? जुड़ा संदर्भ कहता है कि fdयह पहला तर्क है read()। आप इसे नग्न क्यों कहते हैं?
गीक

3
@ गीक मानक पुस्तकालय के FILE *प्रकार की तुलना में , पूर्णांक फ़ाइल डिस्क्रिप्टर "कम लिपटे", अर्थात "नग्न" है।
खोलना

57

एक बफर ( FILE *) है और दूसरा नहीं है। व्यवहार में, आप FILE *लगभग हमेशा उपयोग करना चाहते हैं जब आप एक 'वास्तविक' फ़ाइल (यानी ड्राइव पर) से पढ़ रहे हैं, जब तक कि आप नहीं जानते कि आप क्या कर रहे हैं या जब तक कि आपकी फ़ाइल वास्तव में सॉकेट या ऐसा नहीं है ..

आप फ़ाइल डिस्क्रिप्टर का FILE *उपयोग करके प्राप्त कर सकते हैं fileno()और आप FILE *एक फ़ाइल डिस्क्रिप्टर का उपयोग करके बफ़र खोल सकते हैंfdopen()


12
+1 फाइलो () को इंगित करने के लिए, मैन पेजों का संगठन इसे खोजने के लिए कठिन बनाता है। Fdopen () के लिए भी।
रिविलहिल

20

एक फाइल डिस्क्रिप्टर सिर्फ एक पूर्णांक है जो आपको POSIX open()कॉल से मिलता है । मानक सी का उपयोग करके fopen()आपको एक FILEसंरचना वापस मिलती है । इस FILEसंरचना में अन्य चीज़ों जैसे अंत फ़ाइल और त्रुटि संकेतक, स्ट्रीम स्थिति आदि के बीच यह फ़ाइल विवरणक है।

तो उपयोग करने fopen()से आपको एक निश्चित मात्रा में अमूर्तता मिलती है open()। सामान्य तौर पर आप का उपयोग किया जाना चाहिए fopen()क्योंकि यह अधिक पोर्टेबल है और आप सभी अन्य मानक सी फ़ंक्शन का उपयोग कर सकते हैं जो FILEसंरचना, अर्थात fprintf()और परिवार का उपयोग करता है ।

कोई प्रदर्शन समस्याएँ भी नहीं हैं।


8
पोर्टेबिलिटी लाने के लिए +1। फ़ाइल मानक C लाइब्रेरी (C89 / C90 पर वापस) का हिस्सा है; फ़ाइल विवरणक नहीं हैं।
टॉमलॉजिक

15

फ़ाइल डिस्क्रिप्टर बनाम फ़ाइल पॉइंटर

फ़ाइल विवरणक:

फ़ाइल डिस्क्रिप्टर open()सिस्टम कॉल द्वारा लौटाया गया एक पूर्णांक मान है ।

int fd = open (filePath, mode);

  1. निम्न / कर्नेल स्तर हैंडलर।
  2. पढ़ने और () लिखने के लिए UNIX सिस्टम कॉल का ()।
  3. इसमें बफ़रिंग और ऐसी सुविधाएँ शामिल नहीं हैं।
  4. कम पोर्टेबल और दक्षता की कमी है।

फ़ाइल पॉइंटर:

फ़ाइल पॉइंटर fopen(), लाइब्रेरी फ़ंक्शन द्वारा लौटाए गए C संरचना के लिए एक पॉइंटर है , जिसका उपयोग किसी फ़ाइल की पहचान करने के लिए किया जाता है , फ़ाइल डिस्क्रिप्टर, बफरिंग कार्यक्षमता और I / O ऑपरेशन के लिए आवश्यक सभी अन्य कार्यक्षमता को लपेटता है । फ़ाइल पॉइंटर टाइप FILE का है , जिसकी परिभाषा है। "/usr/include/stdio.h" में पाया जा सकता है । यह परिभाषा एक संकलक से दूसरे में भिन्न हो सकती है।

FILE *fp = fopen (filePath, mode);

// A FILE Structure returned by fopen 
    typedef struct 
    {
        unsigned char   *_ptr;
        int     _cnt;
        unsigned char   *_base;
        unsigned char   *_bufendp;
        short   _flag;
        short   _file;
        int     __stdioid;
        char    *__newbase;
#ifdef _THREAD_SAFE
        void *_lock;
#else
        long    _unused[1];
#endif
#ifdef __64BIT__
        long    _unused1[4];
#endif /* __64BIT__ */
    } FILE;
  1. यह उच्च स्तरीय इंटरफ़ेस है।
  2. फ़्रेड () और फ़ॉरराइट () फ़ंक्शंस में उत्तीर्ण।
  3. इसमें बफरिंग, एरर इंडिकेशन और ईओएफ डिटेक्शन आदि शामिल हैं।
  4. उच्च पोर्टेबिलिटी और दक्षता प्रदान करता है।

1
क्या आप उस उच्च दक्षता दावे का समर्थन करने में सक्षम हैं? मैंने ऐसा कभी नहीं सुना।
गीदड़

1
बफरिंग के कारण "दक्षता" का दावा किया जा सकता है। फ़ाइल डिस्क्रिप्टर के साथ, हर पढ़ा () या लिखना () एक syscall है, और प्रत्येक syscall को महंगा माना जाना चाहिए। FILE * के साथ, बफ़रिंग का अर्थ है कि कुछ पढ़े और लिखे जाए तो syscalls नहीं होगा।
माइक भाला

12

ऐसे बिंदु जोड़ना चाहते हैं जो उपयोगी हो सकते हैं।

के बारे में FILE *

  1. इंटरप्रोसेस संचार (IPC) के लिए इस्तेमाल नहीं किया जा सकता है।
  2. इसका उपयोग तब करें जब आपको जनरलीय उद्देश्य की आवश्यकता होती है I / O। (Printf, frpintf, snprintf, scanf)
  3. मैं इसे डिबग लॉग के लिए कई बार उपयोग करता हूं। उदाहरण,

                 FILE *fp;
                 fp = fopen("debug.txt","a");
                 fprintf(fp,"I have reached till this point");
                 fclose(fp);

के बारे में FILE DESCRIPTOR

  1. यह आमतौर पर आईपीसी के लिए उपयोग किया जाता है।

  2. * Nix सिस्टम (डिवाइस, फाइल, सॉकेट, आदि) पर फ़ाइलों के लिए निम्न-स्तरीय नियंत्रण देता है, इसलिए इससे अधिक शक्तिशाली है FILE *


क्या आप fdopen()IPC और उपकरणों जैसी चीजों का उपयोग करने के लिए नहीं कर सकते हैं FILE*?
ऑसविन

दरअसल, हां और ना दोनों। आप IPC के साथ सेटअप और इनिशियलाइज़ नहीं FILE*कर सकते हैं, लेकिन आप FILE*एक फ़ाइल डिस्क्रिप्टर ( fdopen()) से बना सकते हैं और बाद में वसीयतनामा को बंद कर FILEदेंगे। इसलिए, आप आईपीसी कर सकते हैं , लेकिन आपको किसी भी प्रत्यक्ष आईपीसी को सुविधाजनक बनाने के लिए फ़ाइल विवरणकर्ताओं से थोड़ा सा निपटना होगा।
मीका डब्ल्यू

3

FILE *जब आप, पाठ फ़ाइलें और उपयोगकर्ता इनपुट / आउटपुट के साथ काम है क्योंकि यह आप एपीआई कार्यों की तरह उपयोग करने के लिए अनुमति देता है और अधिक उपयोगी है sprintf(), sscanf(), fgets(), feof()आदि

फ़ाइल डिस्क्रिप्टर एपीआई निम्न-स्तर है, इसलिए यह सॉकेट्स, पाइप, मेमोरी-मैप्ड फ़ाइलों (और नियमित रूप से फाइलें, निश्चित रूप से) के साथ काम करने की अनुमति देता है।


1
+1 क्योंकि आपने मेमोरी मैप की गई फ़ाइलों को जोड़ा है, मेरे वर्तमान पढ़ने के बाद से, अन्य उत्तर पहले से ही दिए गए हैं।
ernie.cordell

3

चर्चा समाप्त करने के लिए बस एक नोट (यदि रुचि हो) ...।

fopenअसुरक्षित हो सकता है, और आप शायद का उपयोग करना चाहिए fopen_sया openसेट विशेष बिट्स के साथ। C1X पेशकश कर रहा है xमोड, तो आप कर सकते हैं fopenमोड के साथ "rx", "wx"आदि

यदि आप उपयोग करते हैं open, तो आप विचार कर सकते हैं open(..., O_EXCL | O_RDONLY,... )या open(..., O_CREAT | O_EXCL | O_WRONLY,... )

उदाहरण के लिए, fopen () और फ़ाइल निर्माण के बारे में धारणा न बनाएं


जैसा कि इसके fopen_sसाथ उपलब्ध होना प्रतीत नहीं होता है POSIX, मुझे लगता है कि सबसे अधिक पोर्टेबल स्पिरिटेशन open(2)और फिर होगा fdopen(2)। (खिड़कियों को एक तरफ छोड़कर)। इसके अलावा, तेजी से fopen_s()या open(2)उसके बाद क्या होगा fdopen(2)?
मिहिर

1

सिस्टम कॉल ज्यादातर फाइल डिस्क्रिप्टर का उपयोग कर रहे हैं, उदाहरण के लिए readऔर write। लाइब्रेरी फ़ंक्शन फ़ाइल पॉइंटर्स ( printf, scanf) का उपयोग करेगा । लेकिन, लाइब्रेरी फ़ंक्शंस केवल आंतरिक रूप से सिस्टम कॉल का उपयोग कर रहे हैं।


मुझे यकीन नहीं है कि आप यह क्यों कह रहे हैं कि लाइब्रेरी फ़ंक्शंस केवल आंतरिक सिस्टम कॉल का उपयोग कर रहे हैं: यदि आप मानक CI / O (या उस मामले के लिए कोई अन्य) कार्यों का मतलब है, तो मुझे यकीन नहीं है कि (सार्वभौमिक रूप से) सच है। अन्यथा, यह नहीं है कि आपने क्या कहा, इसलिए मैं आपकी पोस्ट की भाषा को थोड़ा साफ करना चाहूंगा। आखिरी वाक्य मुझे चकित कर देता है।
ernie.cordell

1

मुझे यहां एक अच्छा संसाधन मिला , जिससे दोनों के बीच मतभेदों के उच्च स्तर का अवलोकन हुआ:

जब आप किसी फ़ाइल में इनपुट या आउटपुट करना चाहते हैं, तो आपके पास अपने प्रोग्राम और फ़ाइल के बीच कनेक्शन का प्रतिनिधित्व करने के लिए दो बुनियादी तंत्रों का विकल्प होता है: फ़ाइल डिस्क्रिप्टर और स्ट्रीम। फ़ाइल डिस्क्रिप्टर को टाइप इंट की वस्तुओं के रूप में दर्शाया जाता है, जबकि धाराओं को FILE * ऑब्जेक्ट के रूप में दर्शाया जाता है।

फ़ाइल डिस्क्रिप्टर इनपुट और आउटपुट संचालन के लिए एक आदिम, निम्न-स्तरीय इंटरफ़ेस प्रदान करते हैं। फाइल डिस्क्रिप्टर और स्ट्रीम दोनों एक डिवाइस (जैसे एक टर्मिनल), या किसी अन्य प्रक्रिया के साथ संचार के लिए एक पाइप या सॉकेट के लिए एक कनेक्शन का प्रतिनिधित्व कर सकते हैं, साथ ही साथ एक सामान्य फ़ाइल भी। लेकिन, यदि आप नियंत्रण कार्य करना चाहते हैं जो एक विशेष प्रकार के उपकरण के लिए विशिष्ट है, तो आपको एक फ़ाइल विवरणक का उपयोग करना चाहिए; इस तरह धाराओं का उपयोग करने के लिए कोई सुविधाएं नहीं हैं। यदि आपके प्रोग्राम को विशेष मोड में इनपुट या आउटपुट करने की आवश्यकता है, जैसे कि नॉनब्लॉकिंग (या पोलेड) इनपुट (फाइल स्टेटस फ्लैग देखें) तो आपको फाइल डिस्क्रिप्टर का भी उपयोग करना चाहिए।

धाराएँ एक उच्च-स्तरीय इंटरफ़ेस प्रदान करती हैं, जो आदिम फ़ाइल डिस्क्रिप्टर सुविधाओं के शीर्ष पर स्तरित होती हैं। स्ट्रीम इंटरफ़ेस सभी प्रकार की फ़ाइलों को बहुत समान रूप से मानता है - एकमात्र अपवाद बफ़रिंग की तीन शैलियाँ हैं जिन्हें आप चुन सकते हैं (स्ट्रीम बफरिंग देखें)।

स्ट्रीम इंटरफ़ेस का उपयोग करने का मुख्य लाभ यह है कि धाराओं पर वास्तविक इनपुट और आउटपुट ऑपरेशन (नियंत्रण संचालन के लिए विरोध के रूप में) करने के लिए फ़ंक्शन का सेट फ़ाइल डिस्क्रिप्टर के लिए संबंधित सुविधाओं की तुलना में बहुत समृद्ध और अधिक शक्तिशाली है। फ़ाइल डिस्क्रिप्टर इंटरफ़ेस वर्णों के ब्लॉक को स्थानांतरित करने के लिए केवल सरल फ़ंक्शन प्रदान करता है, लेकिन स्ट्रीम इंटरफ़ेस शक्तिशाली स्वरूपित इनपुट और आउटपुट फ़ंक्शन (प्रिंटफ और स्कैनफ) के साथ-साथ चरित्र- और लाइन-ओरिएंटेड इनपुट और आउटपुट के लिए फ़ंक्शन भी प्रदान करता है।

चूँकि फाइल डिस्क्रिप्टर के संदर्भ में धाराएँ लागू की जाती हैं, आप फाइल डिस्क्रिप्टर को एक स्ट्रीम से निकाल सकते हैं और फाइल डिस्क्रिप्टर पर सीधे निम्न-स्तरीय ऑपरेशन कर सकते हैं। आप शुरुआत में एक फाइल डिस्क्रिप्टर के रूप में एक कनेक्शन भी खोल सकते हैं और फिर उस फाइल डिस्क्रिप्टर से जुड़ी एक स्ट्रीम बना सकते हैं।

सामान्य तौर पर, आपको फ़ाइल डिस्क्रिप्टर के बजाय स्ट्रीम का उपयोग करना चाहिए, जब तक कि कुछ विशिष्ट ऑपरेशन नहीं करना चाहते हैं जो केवल फ़ाइल डिस्क्रिप्टर पर किया जा सकता है। यदि आप एक शुरुआत प्रोग्रामर हैं और सुनिश्चित नहीं हैं कि किस फ़ंक्शन का उपयोग करना है, तो हमारा सुझाव है कि आप स्वरूपित इनपुट फ़ंक्शंस (फ़ॉर्मेट किए गए इनपुट देखें) और फ़ॉर्मेट किए गए आउटपुट फ़ंक्शंस (फ़ॉर्मेट किए गए आउटपुट देखें) पर ध्यान केंद्रित करें।

यदि आप अपने कार्यक्रमों की जीएनयू के अलावा अन्य प्रणालियों के पोर्टेबिलिटी के बारे में चिंतित हैं, तो आपको यह भी पता होना चाहिए कि फ़ाइल विवरणक स्ट्रीम के रूप में पोर्टेबल नहीं हैं। आप ISO C को स्ट्रीम के समर्थन में चलाने वाले किसी भी सिस्टम की अपेक्षा कर सकते हैं, लेकिन गैर-GNU सिस्टम फ़ाइल डिस्क्रिप्टर का समर्थन नहीं कर सकते हैं या केवल GNU फ़ंक्शंस के सबसेट को लागू कर सकते हैं जो फ़ाइल डिस्क्रिप्टर पर काम करते हैं। GNU C लाइब्रेरी में फ़ाइल डिस्क्रिप्टर फ़ंक्शंस में से अधिकांश POSIX.1 मानक में शामिल हैं, हालाँकि।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.