2009-12-21 12 views
5

मैं एक सी ++ पुस्तकालय है कि एक बाइनरी फ़ाइल में अपने डेटा (कस्टम structs आदि का संग्रह) की बचत होती है लिखा है। मैं वर्तमान में उपयोग (अर्थात बनाने और उपभोग) फ़ाइलें स्थानीय रूप से, मेरे Windows (XP) मशीन पर। सरलता के लिए, की सुविधा देता है दो भागों में पुस्तकालय के बारे में सोच: एक लेखक (फ़ाइलें बनाता है) और एक पाठक या उपभोक्ता (बस फ़ाइलों से डेटा पढ़ता है)।बाइनरी फ़ाइलें और पार मंच संगतता

हाल ही में हालांकि, मैं भी मेरी Linux मशीन पर उपभोग करने के लिए (अर्थात पढ़ें) डेटा मैं बनाया है फ़ाइलें मेरी XP मशीन, पर चाहते हैं। मुझे इस चरण में इंगित करना होगा कि दोनों मशीनें पीसी हैं (इसलिए एंडियनस आदि) हैं।

मैं एक पाठक का निर्माण कर सकते हैं (और लिनक्स के लिए संकलन [Ubuntu 9.10 सटीक होना करने के लिए]), के बाद से मैं पुस्तकालय निर्माता हूँ। मेरा प्रश्न, इससे पहले कि मैं नीचे इस सड़क (पाठक आदि के निर्माण के) शुरू होता है:

मान लिया जाये कि मैं सफलतापूर्वक लिनक्स के लिए पाठक का निर्माण किया है,

मैं बस कॉपी कर सकते हैं करवाते हैं, फ़ाइलों को थे पर बनाया विंडोज़ (एक्सपी) मशीन लिनक्स (उबंटू 9 .10) मशीन पर मशीन और कॉपी की गई फाइल को सफलतापूर्वक पढ़ने के लिए लिनक्स रीडर का उपयोग करें?

+0

आपको परिभाषित करना होगा कि "बाइनरी फ़ाइल" से आपका क्या मतलब है। क्या आप 'fwrite' का उपयोग करके' struct' डेटा इत्यादि जैसी चीजें लिखते हैं? क्या आप सब कुछ बाइट्स में विघटित करते हैं और फिर डेटा लिखते हैं? –

+1

सभी शॉर्टिंग के साथ क्या है? आप ** जोर ** के लिए तारों का उपयोग कर सकते हैं और यह अधिक पठनीय है ... – danio

+0

@ डैनियो वह डॉस से आता है, जहां सभी चीजें हैं – zeitue

उत्तर

14

फ़ाइलों के लिए द्विआधारी संगत होना:

  • endianness से मेल खाना चाहिए (क्योंकि यह आप के लिए करता है)
  • bitfield पैकिंग आदेश में एक ही
  • आकार और प्रकार के समान होना चाहिए की signedness होना चाहिए
  • संकलक गद्दी और संरेखण

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

+0

हाय moonshadow, प्रतिक्रिया के लिए धन्यवाद। क्या आप कुछ और विस्तार कर सकते हैं - जब आपके पास समय होता है, जिसमें एक साधारण श्रेणी का उपयोग किया जाता है जिसमें एक std :: vector होता है, तो मैं संवेदनात्मक जांच, और/या सेंडिनल सदस्यों द्वारा आपका क्या मतलब है, समझदारी से समझने में सक्षम हूं। इन चेकों को लागू करने के बारे में सोचने का एकमात्र तरीका सीमाओं में परिभाषित स्थिरांक का उपयोग करके होगा - क्या आपका मतलब है? - या शायद आपके पास एक और अधिक सुरुचिपूर्ण दृष्टिकोण है? –

+0

इसके अलावा, मुझे यकीन नहीं है कि कैसे जांचें 2, 3 और 4 (जो आपने ऊपर सूचीबद्ध किया है) सही है। मैं एक्सपी पर वीएस 2008 का उपयोग कर रहा हूं, और उबंटू पर जीसीसी 4.4.1 का उपयोग कर रहा हूं - इस बात पर कोई सुझाव है कि मैं कैसे जांच सकता हूं कि इन आवश्यकताओं का उल्लंघन नहीं किया गया है? –

+2

@ इसे चिपकाएं: "सेंटीनेल सदस्यों" द्वारा, मेरा मतलब है कि आपकी फ़ाइल में लिखे गए शीर्ष-स्तरीय संरचनाओं को एक ज्ञात निरंतर मूल्य वाला सदस्य रखने के लिए, और फ़ाइल के अंत में एक को भी रखें; लोड समय पर, जांचें कि इन सदस्यों में आपके द्वारा अपेक्षित मूल्य शामिल है - इसमें कंपेलरों के बीच भिन्न आकार/पैडिंग के साथ समस्याएं होनी चाहिए। – moonshadow

2

बाइनरी फ़ाइलों को समान अंतहीनता वाली मशीनों में संगत होना चाहिए।

मुद्दा आप अपने कोड में हो सकता है ints का आकार है, वहीं यह आवश्यक कल्पना नहीं कर सकते अलग ओएस पर संकलक एक ही आकार के पूर्णांक है। तो या तो बाइट्स के ब्लॉक कॉपी और उन्हें डाली, या उपयोग int16, int32 आदि

1

हैं:

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

तो हाँ, आपकी फ़ाइलों को पोर्टेबल होना चाहिए।

तीसरा बुलेट पॉइंट एक फ़ाइल प्रारूप को "पोर्टेबल" बनाता है। आपके structs में आपके किस प्रकार के डेटा के आधार पर, यह बहुत आसान या थोड़ा मुश्किल हो सकता है। बिटफिल्ड, या डेटा को एक अलग प्रकार से दोबारा परिभाषित किया जा रहा है विशेष रूप से मुश्किल है।

1

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

1

स्ट्रक्चर फ़ाइल प्रारूप नहीं हैं, और आपको उन्हें इस तरह उपयोग करने की कोशिश नहीं करनी चाहिए।

structs को fread और fwrite के साथ काम करने का प्रयास करते समय, इसे काम करने के लिए बड़ी संख्या में हैक हैं। आप बाइट-स्वैप पूर्णांक ताकि आप छोटी-छोटी और बड़ी-अंत मशीनों के बीच फ़ाइलों को साझा कर सकें। आप निश्चित-चौड़ाई पूर्णांक प्रकारों का उपयोग करने के लिए अपने structs को बदलते हैं, ताकि आप अलग-अलग शब्द आकारों (जैसे कि x86 और x64 मशीनों के बीच) के बीच मशीनों के बीच साझा कर सकें। आप कंपाइलर संस्करणों के बीच साझा करने के लिए structs के पैडिंग को नियंत्रित करने के लिए कंपाइलर-विशिष्ट pragmas जोड़ें।

यह काम करता है, लेकिन यह बदसूरत है। उल्लेख नहीं है, गलत पाने के लिए आसान है।

The byte order fallacy में सिफारिश की तरह ही, फ़ील्ड को अलग-अलग पढ़ने/लिखने के लिए कोड लिखना एक बेहतर विचार है। अपना कोड लिखकर, आप सुनिश्चित कर सकते हैं कि कोई पैडिंग नहीं है, और आप पूर्णांक के स्थानीय आकार से स्वतंत्र रूप से पूर्णांक आकार चुन सकते हैं, और आप बाइट-स्वैपिंग के बिना दोनों एंडियननेस का समर्थन कर सकते हैं (एक पूर्णांक के बाइट्स को अलग/लिखकर)।

हैकी दृष्टिकोण के विपरीत, यह गलत होना मुश्किल है। इसके अलावा, क्योंकि आप किसी भी कंपाइलर या आर्किटेक्चर विशिष्ट व्यवहार पर भरोसा नहीं करते हैं, या तो आपका कोड सभी कंपाइलर्स और आर्किटेक्चर, या कोई भी काम करेगा। यदि आप इसे सही करते हैं, तो आपके पास कोई प्लेटफॉर्म-विशिष्ट बग नहीं होना चाहिए।

एक नकारात्मक है; फ़ील्ड को व्यक्तिगत रूप से पढ़ना/लिखना सीधे फ्रेड/फेराइट का उपयोग करने से धीमा होगा। आप एक बफर (uint8_t buffer[]) सेट कर सकते हैं और उसमें डेटा की संपूर्णता लिख ​​सकते हैं, और फिर एक बार में सबकुछ लिख सकते हैं, जो मदद कर सकता है, लेकिन यह अभी भी धीमा हो जाएगा (क्योंकि आपको अभी भी फ़ील्ड को स्थानांतरित करना होगा एक समय में बफर), लेकिन अधिकांश उद्देश्यों के लिए यह अभी भी पर्याप्त तेज़ होगा (अपवाद/रीयल-टाइम सिस्टम या अत्यधिक उच्च प्रदर्शन कंप्यूटिंग होने के अपवाद)।

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