محتوى ملف الإخراج الثنائي الذي تم إنشاؤه باستخدام دفق الإخراج

StackOverflow https://stackoverflow.com/questions/684931

  •  22-08-2019
  •  | 
  •  

سؤال

يتم تجميع هذا الرمز وتنفيذه.إنه ببساطة طباعة المحتوى إلى تنسيق ثنائي.لكن الناتج يختلف عما توقعته، وهو:

  1. يجب أن يكون حجم ملف الإخراج أصغر بكثير من تلك التي تم إنشاؤها باستخدام std::cout.
  2. يجب ضغط محتوى ملف الإخراج ، وبالتالي عندما نفتحه في المحرر ، يجب ألا نتمكن من رؤية المحتوى.

ولكن لماذا لا يعمل الكود أدناه كما آمل أن يفعل؟كيف يمكنني تعديله وفقا لذلك؟

#include <iostream>
#include <vector>
#include <fstream>
#include <string>
#include <sstream>
using namespace std;

void WriteStr2BinFh(const string& St, ostream &fn)
{
   fn.write(St.c_str(), St.length());
}



int main  ( int arg_count, char *arg_vec[] ) {

    vector <string> Tags;
   // In principle we have millions of such tags
   // Hence we need to compress it into binary output.
    Tags.push_back("0000000000");
    Tags.push_back("0000101110");
    Tags.push_back("0133030122");
    Tags.push_back("0133132033");
    Tags.push_back("1002013320");
    Tags.push_back("1111111111");
    Tags.push_back("1301013133");
    Tags.push_back("3010112111");
    Tags.push_back("3203012113");
    Tags.push_back("3203012212");

    //prn_vec<string>(Tags, "\t");
    //cout << endl;

    ofstream outfile;
    outfile.open("MyOut.bin", ios::binary|ios::out);

    for (unsigned i=0; i <Tags.size(); i++) {
         WriteStr2BinFh(Tags[i]+"\t",outfile);
    }

    outfile.close();

    return 0;
}
هل كانت مفيدة؟

المحلول

يجب عليك كتابة البيانات بتنسيق ثنائي (وليس نصًا):

void WriteStr2BinFh(const string& St, ostream &fn)
{
char *p = 0;
long l = strtol(St.c_str(), &p);
fn << l;
}

يجب أن تدرك أن الأنواع مثل long لها بعض القيم القصوى، لذلك ربما يتعين عليك تقسيم السلسلة إلى أجزاء n وحفظها كـ n longs.

نصائح أخرى

يجب أن يكون حجم ملف الإخراج كثيرا أصغر من تلك التي تم إنشاؤها باستخدام الأمراض المنقولة جنسيا :: كوت

ماذا تقصد "تم إنشاؤه باستخدام std::cout"؟
يمكن أن يكون أصغر قليلاً إذا قمت بحفظ ints، وليس سلاسل.

يجب أن يكون محتوى ملف الإخراج مضغوط ، وبالتالي عندما نفتحه في محرر ، لا ينبغي أن نكون قادرين على رؤية المحتوى.

لا، لا ينبغي أن تكون مضغوطة.يمكنك استخدام مكتبة Boost.Iostreams http://www.boost.org/doc/libs/1_38_0/libs/iostreams/doc/index.html لإنشاء ملفات مضغوطة.

لسهولة الفهم، قد تعتقد أن الملف الثنائي يحتوي على معلومات يمكنك رؤيتها في مصحح الأخطاء عند البحث في الذاكرة.

أيضًا للإخراج بتنسيق ثنائي، يجب عليك استخدام طريقة دفق الكتابة لجميع العناصر المتجهة (في حالة std::vector < int > سيكون له فرق).(للإخراج يمكنك استخدام عامل التشغيل << )

يجب أن يتم ضغط محتوى ملف الإخراج، وبالتالي عندما نفتحه في المحرر، يجب ألا نكون قادرين على رؤية المحتوى.

أخشى أن مكتبة IOStream لا تطبق أي ضغط على مخرجاتك.كما أشار bb، يجب عليك استخدام مكتبة أخرى لضغط الدفق الخاص بك.

يجب أن يكون حجم ملف الإخراج أصغر بكثير من تلك التي تم إنشاؤها باستخدام std::cout.

كنتيجة للوسيطة السابقة، تتم كتابة الإخراج، الذي يتم التعامل معه على أنه دفق من البايتات (التي تصادف أنها أحرف ممثلة ASCII) "كما هي" في الملف، وبالتالي، لن يتغير الحجم.

نلقي نظرة على بعض توثيق و أ تفسير أفضل الملفات الثنائية بشكل عام

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top