C ++:服务器上的boost :: filesystem问题(locale :: facet :: _ S_create_c_locale名称无效)

时间:2013-10-16 13:51:16

标签: c++ boost ubuntu-12.04

我在教师服务器上运行C ++项目时遇到问题。我得到的运行时错误是:

terminate called after throwing an instance of 'std::runtime_error'
what():  locale::facet::_S_create_c_locale name not valid
Aborted (core dumped)

我确定问题出在这个文件系统迭代器中(通过使用测试程序):

bf::path dir("ImageData/" + m_object_type);

vector<bf::path> tmp;
copy(bf::directory_iterator(dir), bf::directory_iterator(), back_inserter(tmp));
sort(tmp.begin(), tmp.end());
for (vector<bf::path>::const_iterator it(tmp.begin()); it != tmp.end(); ++it)
{
    auto name = *it;
    image_names.push_back(name.string());
}

该程序在另外两个基于Linux的系统(kubuntu&amp; linux mint)上完美运行,但由于我的项目运行时很重,并且使用不同的参数运行它需要大约28天才能在我的机器上运行我真的想要使用服务器)。我已经尝试了各种路径,但没有一个工作。我读到有关在1.47之前导致此错误的提升错误,但我在服务器上使用1.54。我还检查了系统区域设置,但这并没有真正给我一个线索,因为它们几乎与我的系统相似。服务器的其他规范是:

Ubuntu 12.04.1 LTS(GNU / Linux 3.2.0-29-通用x86_64) g / c ++(Ubuntu / Linaro 4.6.3-1ubuntu5)4.6.3

如果有人有任何想法分享,我将不胜感激。

3 个答案:

答案 0 :(得分:2)

这是issue with Boost < 1.56。 Boost内部尝试构建std::locale("")(请参阅http://www.boost.org/doc/libs/1_55_0/libs/filesystem/src/path.cpp,并比较v1.56中的更新版本)。如果语言环境(或LC_ALL)无效,则此调用将失败。

就我而言,拨打boost::filesystem::create_directories()的电话会触发locale("")来电。

以下解决方法适用于我:覆盖程序中的LC_ALL环境变量。 std::locale("")似乎使用该变量来确定“合理的默认”区域设置应该是什么。

#include <locale>
#include <cstdlib>
#include <iostream>

int main(int argc, char **)
{
  try {
    std::locale loc("");
    std::cout << "Setting locale succeeded." << std::endl;
  } catch (const std::exception& e) {
    std::cout << "Setting locale failed: " << e.what() << std::endl;
  }

  // Set LC_ALL=C, the "classic" locale
  setenv("LC_ALL", "C", 1);
  // Second attempt now works for me:
  try {
    std::locale loc("");
    std::cout << "Setting locale succeeded." << std::endl;
  } catch (const std::exception& e) {
    std::cout << "Setting locale failed: " << e.what() << std::endl;
  }
}

setenv来电后,我可以创建默认localeboost::filesystem来电也可以。

答案 1 :(得分:-1)

我不确定,但我怀疑这个程序的行为是一样的:

#include <locale>
#include <iostream>
#include <stdexcept>

int main () {
    try { std::locale foo (""); }
    catch ( std::runtime_error & ex ) { std::cout << ex.what() << std::endl; }  
    }

此外,这张(旧)机票https://svn.boost.org/trac/boost/ticket/5289可能会对这个问题有所了解。

编辑:从技术上讲,这不是一个答案。

答案 2 :(得分:-1)

对于任何感兴趣的人,这里是使用QT-lib的上述目录迭代器的一个版本:

string str1 = "ImageData/";
QString dir_string1 = QString::fromStdString(str1);
QString dir_string2 = QString::fromStdString(m_object_type);

dir_string1.append(dir_string2);
QDir dir(dir_string1);

dir.setFilter(QDir::Files);
dir.setSorting(QDir::Name); 

QStringList entries = dir.entryList();

string tmp;

for (QStringList::ConstIterator it=entries.begin(); it != entries.end(); ++it)
{
    auto name = *it;
    tmp = name.toUtf8().constData();
    image_names.push_back(str1 + m_object_type + "/" + tmp);
}