儲存檔案為UTF8格式(Writing UTF-8 files in C++).

來源:互聯網
上載者:User

都是簡單的單詞,我就不翻譯了。

原文地址:http://mariusbancila.ro/blog/2008/10/20/writing-utf-8-files-in-c/

 

Let’s say you need to write an XML file with this content:

< ?xml version="1.0" encoding="UTF-8"? >
< root description="this is a naïve example" >
< /root >

How do we write that in C++?

At a first glance, you could be tempted to write it like this:

#include< fstream >

int main()
{
        std::ofstream testFile;

        testFile.open("demo.xml", std::ios::out| std::ios::binary);

        std::string text =
                "< ?xml version=\"1.0\" encoding=\"UTF-8\"? >\n"
                "< root description=\"this is a naïve example\" >\n< /root >";

        testFile << text;

        testFile.close();

        return0;
}

When you open the file in IE for instance, surprize! It's not rendered correctly:

So you could be tempted to say "let's switch to wstring and wofstream".

int main()
{
        std::wofstream testFile;

        testFile.open("demo.xml", std::ios::out| std::ios::binary);

        std::wstring text =
                L"< ?xml version=\"1.0\" encoding=\"UTF-8\"? >\n"
                L"< root description=\"this is a naïve example\" >\n< /root >";

        testFile << text;

        testFile.close();

        return0;
}

And when you run it and open the file again, no change. So, where is the problem? Well, the problem is that neither ofstream nor wofstream write the text in a UTF-8 format. If you want the file to really be in UTF-8 format, you have to encode the output buffer in UTF-8. And to do that we can use WideCharToMultiByte(). This Windows API maps a wide character string to a new character string (which is not necessary from a multibyte character set). The first argument indicates the code page. For UTF-8 we need to specify CP_UTF8.

The following helper functions encode a std::wstring into a UTF-8 stream, wrapped into a std::string.

#include< windows.h >

std::string to_utf8(constwchar_t* buffer,int len)
{
        int nChars =::WideCharToMultiByte(
                CP_UTF8,
                0,
                buffer,
                len,
                NULL,
                0,
                NULL,
                NULL);
        if(nChars ==0)return"";

        string newbuffer;
        newbuffer.resize(nChars);
        ::WideCharToMultiByte(
                CP_UTF8,
                0,
                buffer,
                len,
                const_cast<char*>(newbuffer.c_str()),
                nChars,
                NULL,
                NULL);

        return newbuffer;
}

std::string to_utf8(const std::wstring& str)
{
        return to_utf8(str.c_str(),(int)str.size());
}

With that in hand, all you have to do is doing the following changes:

int main()
{
        std::ofstream testFile;

        testFile.open("demo.xml", std::ios::out| std::ios::binary);

        std::wstring text =
                L"< ?xml version=\"1.0\" encoding=\"UTF-8\"? >\n"
                L"< root description=\"this is a naïve example\" >\n< /root >";

        std::string outtext = to_utf8(text);

        testFile << outtext;

        testFile.close();

        return0;
}

And now when you open the file, you get what you wanted in the first place.

And that is all!

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.