C++ C++;要正确使用cout wcout ifstream读取带有重音字符的文本文件

C++ C++;要正确使用cout wcout ifstream读取带有重音字符的文本文件,c++,ubuntu,locale,ifstream,C++,Ubuntu,Locale,Ifstream,我想在Ubuntu 20.04上读取一个txt编码的UTF8文件 我在wcout cout和ifstream中添加了区域设置fr_fr.UTF-8 我在想,仅仅添加区域设置就足够了 输出结果如下: 这是我的密码 ... #include <iostream> #include <fstream> #include <ctime> #include <cstdlib> #include <vector> #include <str

我想在Ubuntu 20.04上读取一个txt编码的UTF8文件

我在wcout cout和ifstream中添加了区域设置fr_fr.UTF-8

我在想,仅仅添加区域设置就足够了

输出结果如下:

这是我的密码

...
#include <iostream>
#include <fstream>
#include <ctime>
#include <cstdlib>
#include <vector>
#include <string>
#include <locale>
#include <codecvt>
    
int main(int argc, char** argv){
    
    int nbreLigne;
    std::vector<std::wstring> dico;
    std::string path("liste_test.txt");
    std::wstring ligne;
    
    std::locale loc("fr_FR.UTF-8");
    std::cout.imbue(loc);
    std::wcout.imbue(loc);
    std::wifstream file(path.c_str(), std::ios::in);
    file.imbue(loc);
    std::cout << "Path = " << path << std::endl;
    std::cout << "1- locale wifstream : " << file.getloc().name() << std::endl;
    std::cout << "2- locale wcout : " << std::wcout.getloc().name() << std::endl;
    std::cout << "3- locale cout : " <<  std::cout.getloc().name() << std::endl;
    /* Pas d'erreur de compile mais ne semble pas avoir d'effet 
    file.imbue(std::locale(file.getloc(), new std::codecvt_utf8<wchar_t, 0x10ffff, std::consume_header>));
    std::cout << "1- Variable de localisation : " << file.getloc().name();
    */

    if (file){
        
        //compte les lignes      
        while (std::getline(file, ligne)){
            nbreLigne++;
            dico.push_back(ligne);

            /*
            Erreur de segmentation (core dumped) si cette ligne est activée
            std::wcout << dico[nbreLigne] << std::endl; 
            */
        }
    
        std::cout << "Total lines number = " << nbreLigne << std::endl;
        
    }
    else{
        std::cout << "ERREUR: Impossible d'ouvrir le fichier." << std::endl;
    }

    std::cout << "-------------------" << std::endl;
    std::cout << "Lecture de la variable dico" << std::endl;
    std::cout << std::endl;
    for(int i = 0; i < nbreLigne; i++){
       std::wcout << dico[i] << std::endl;
    }
    
...
。。。
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括
int main(int argc,字符**argv){
内特恩布雷涅;
std::矢量dico;
字符串路径(“liste_test.txt”);
std::wstring-ligne;
标准::现场位置(“fr_fr.UTF-8”);
标准:电流注入(loc);
标准:wcout.imbue(loc);
std::wifstream文件(path.c_str(),std::ios::in);
文件.imbue(loc);

std::cout简单地说,在C++和大多数编程语言中,没有通用的方法来处理重音字符。只有ASCII几乎是通用的,并且只包含英语字符。随着时间的推移,处理语言特定字符的多种解决方案从一个到另一个诞生了(
std::wcout
用于那些宽字符)

您的问题不在于您的程序(除非在本例中它只应使用
std::cout
),而在于您的字典使用了与终端不同的字符集

解决字符集问题既困难又无聊。在您的情况下,用UTF-8或使用手工重写字典是值得的。在实际项目中,您将使用这样的国际化(i18n)工具来处理此负担。今天,大多数现代系统都使用UTF-8


也可以在C++流中设置区域设置,只在不相关的注释时更改程序格式值,如小数分隔符,不需要<代码> nbReReNe> <代码>变量。

@一些程序员都德好的,谢谢你的建议。将UTF-8插入
std::wcout
更有效。基本上,指定你的终端必须是UTF-8终端。事实并非如此。将字符集插入
std::cout
或任何其他字符流似乎没有任何用处。最后,混合使用
cout
wcout
需要非常小心地使用显式刷新。@Sam Varshavchik我在Ubuntu上。我的终端在UTF8 UnicodeIf上如果你正在阅读UTF-8内容,并且你的终端是UTF-8,那么你希望嵌入UTF-8语言环境能实现什么呢?它不会做任何事情。