2015-01-02 12 views
7

Clang (Apple LLVM sürüm 6.0 (clang-600.0.56) (LLVM 3.5svn, Hedef: x86_64-apple-darwin14.0.0 temel alınarak), C++ 11 ve CGAL'yi karıştırmaya çalışırken ilginç bir sorunla karşılaştım (.) MacPorts aracılığıylaClang'ın C++ 11 desteği güvenilir midir?

Ben std::vector<>::reserve çağrı olsun veya olmasın programım bile derlemek olacak belirleyecek gibi görünüyor CGAL örnekler olsun

minimal olarak (minimal örnek haline sorunu aşağı kesilmiş ettik).:

#include <vector> 
#include <CGAL/Exact_predicates_inexact_constructions_kernel.h> 
#include <CGAL/AABB_tree.h> 
#include <CGAL/AABB_traits.h> 
#include <CGAL/AABB_triangle_primitive.h> 

// CGAL::Epeck works fine, suggesting the problem is in CGAL::Epick 
typedef CGAL::Epick Kernel; 
typedef CGAL::Triangle_3<Kernel> Triangle_3; 
typedef typename std::vector<Triangle_3>::iterator Iterator; 
typedef CGAL::AABB_triangle_primitive<Kernel, Iterator> Primitive; 
typedef CGAL::AABB_traits<Kernel, Primitive> AABB_triangle_traits; 
typedef CGAL::AABB_tree<AABB_triangle_traits> Tree; 
typedef typename Tree::Point_and_primitive_id Point_and_primitive_id; 
typedef CGAL::Point_3<Kernel> Point_3; 

template <typename BKernel> 
void A() 
{ 
    const CGAL::AABB_tree< 
    CGAL::AABB_traits<BKernel, 
     CGAL::AABB_triangle_primitive<BKernel, 
     typename std::vector<CGAL::Triangle_3<BKernel> >::iterator 
     > 
    > 
    > tree; 
    Point_and_primitive_id pp = tree.closest_point_and_primitive(Point_3()); 
} 

void B() 
{ 
    std::vector<Triangle_3> T; 
#ifdef MAGIC 
    T.reserve(0); 
#endif 
    return A<Kernel>(); 
} 

Düzenlenmesi:

Bu, derlenemiyor.

In file included from example.cpp:1: 
    In file included from /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/vector:265: 
    In file included from /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/__bit_reference:15: 
    In file included from /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/algorithm:626: 
    In file included from /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/utility:157: 
    /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/__tuple:228:60: error: 
      no member named 'value' in 'std::__1::is_convertible<const CGAL::Point_3<CGAL::Epick> &, 
      CGAL::Point_3<CGAL::Epick> >' 
            is_convertible<_Tp0, _Up0>::value && 
            ~~~~~~~~~~~~~~~~~~~~~~~~~~~~^ 

/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1/__tuple:242:14: note: 
      in instantiation of template class 'std::__1::__tuple_convertible_imp<true, std::__1::__tuple_types<const 
      CGAL::Point_3<CGAL::Epick> &, const CGAL::Vector_3<CGAL::Epick> &>, 
      std::__1::__tuple_types<CGAL::Point_3<CGAL::Epick>, CGAL::Vector_3<CGAL::Epick> > >' requested here 
     : public __tuple_convertible_imp<tuple_size<typename remove_reference<_Tp>::type>::value == 

Ancak bu veren, ben std::vector::reserve için bu sihirli arama yaparsanız derlemek yapar:: gibi verilmesi hataları

clang++ -std=c++11 -c example.cpp -I/opt/local/include -DMAGIC 

veya devre dışı bırakma c tarafından ++ 11

clang++ -c example.cpp -I/opt/local/include 
  1. CGAL veya clang'da bu bir hata mı?
  2. Böyle düzensiz derleyici davranışı için ne gibi bir açıklama olabilir?
  3. temiz temizlemenin bir yolu var mı (büyük projeme uyması için çözüme ihtiyacım olduğu için ayarlanan şablon veya işlev prototipini gerçekten değiştirmeden umuyoruz).
+0

Bu, XCode'un "is_convertible" tanımında bir fluke gibi görünüyor, ancak böyle bir hataya sahip olmak aklımın varlığını kabul etmeyi reddettiği kadar olanaksız. Hangi standart kütüphanenin kullanıldığı hakkında bir fikrin var mı? Bu benim clangın kullanmasından farklı bir şey. Hangi mayın olduğunu bilmiyorum ama en önemlisi "Telif Hakkı (C) 2001-2013 Özgür Yazılım Vakfı, Inc." –

+0

Clang libC++ gibi görünüyor, wheras libstdC++ var http://en.wikipedia.org/wiki/Standard_Template_Library#Implementations –

+0

'-stdlib = libC++' işaretini eklerseniz durum değişmez.Bunun yerine '-stdlib = libstdC++' yazıyorsa, hiçbir sürüm derlenmez ve hata gibi hatalar alırım: 'std' adında 'forward' adında bir şablon yok; ' –

cevap

5

Apple'ın GCC'si güncelliğini yitirdiği (2007'den itibaren en son GPL sürüm 2, GCC 4.2.1) ve C++ 11 özelliği tamamlanmadığından (dolayısıyla libstdC++ ile sağlanan), GCC'nin daha modern bir sürümünü yükleyebilirsiniz. MacPorts (sudo port install gcc48 veya sudo port install gcc49) aracılığıyla ve bu size libstdC++ daha modern bir sürümünü sağlayacaktır. Kodunuzu

ile sınandım ve başarıyla derledim.

Bu çözümü tercih ederseniz ve daha temiz bir derleyici çağrısı istiyorsanız; Sadece bir kez

sudo port select --set gcc mp-gcc48 

: Eğer (gcc48 için benim durumumda) komutuyla gcc_select kullanılarak varsayılan olarak MacPorts' GCC ayarlayabilirsiniz. Daha sonra yeni bir oturumda sadece

g++ -std=c++11 -c example.cpp -I/opt/local/include 

ile derleyebilirsiniz.

+0

Açıklama için teşekkürler. Bu benim tipik kurulumumdu, ama şimdi amacım projemi mac üzerine kurulu clang ile derlemektir: bu yüzden derleyicileri değiştirmek istemiyorum. Bu örnekte C++ 11'in hangi özelliği eksik? –

+0

Teşekkür ederim. Sorunuzdaki yorumlara bakıldığında, Apple'ın 'libstdC++' işlevini kullandığınızda std :: forward' eksik gibi görünüyor. Uzun (ama ümitle ödüllendirici) bir yol, MacPortları görmezden gelmek ve CGAL'ı ve tüm bağımlılıklarını yerleşik clang ile derlemek olacaktır. Bunu kendim yapmadım ve eğer bunu yaparsan deneyimini okumak isterdim. Bir alternatif, bu sorunları MacPorts'un denetleyicilerine bildiriyor olabilir ve CGAL ve bağımlılıklarının derleme betiklerini değiştirmelerini bekleyebilir. – mty

+0

Teşekkürler. Sonuç olarak, bu CGAL'de bir hatadır veya Apple'ın libstdC++'sindeki bir hatadır ki, CGAL her nasılsa tökezliyor? –