2010-08-05 33 views
38

मुझे आश्चर्य है कि क्या ट्यूपल प्रारंभकर्ता सूची द्वारा प्रारंभ किया जा सकता है (प्रारंभिककर्ता_सूची के प्रारंभकर्ता_सूची द्वारा अधिक सटीक होना)? टपल परिभाषा को ध्यान में रखते:प्रारंभकर्ता सूची से std :: tuple प्रारंभ करना

static vertex const nullvertex = { {{0, 0, 0}}, 
            {{0.0, 0.0}}, 
            {{0, 0, 0, 0}}, 
            {{0, 0, 0, 0}} }; 

मैं सिर्फ एक ही कार्यक्षमता मैं टपल के बजाय struct का उपयोग कर मिला हासिल करना चाहते हैं (इस प्रकार केवल सरणियों initializer_list द्वारा प्रारंभ किया गया है:

typedef std::tuple< std::array<short, 3>, 
        std::array<float, 2>, 
        std::array<unsigned char, 4>, 
        std::array<unsigned char, 4> > vertex; 

वहाँ निम्न कार्य की किसी भी तरह से है):

static struct vertex { 
    std::array<short, 3> m_vertex_coords; 
    std::array<float, 2> m_texture_coords; 
    std::array<unsigned char, 4> m_color_1; 
    std::array<unsigned char, 4> m_color_2; 
} const nullvertex = { 
    {{0, 0, 0}}, 
    {{0.0, 0.0}}, 
    {{0, 0, 0, 0}}, 
    {{0, 0, 0, 0}} 
}; 

कोई कारण मैं tuples का उपयोग करना चाहिए है, बस सोच रहा। मैं पूछ रहा हूं, क्योंकि मैं g ++ टेम्पलेट त्रुटियों के माध्यम से जाने में असमर्थ हूं जो इस तरह के ट्यूपल प्रारंभिकरण के मेरे प्रयास से उत्पन्न होते हैं।

@Motti: तो मैं वर्दी आरंभीकरण के लिए उचित सिंटैक्स याद किया -

static vertex const nullvertex = vertex{ {{0, 0, 0}}, 
             {{0.0, 0.0}}, 
             {{0, 0, 0, 0}}, 
             {{0, 0, 0, 0}} }; 

और

static vertex const nullvertex{ {{0, 0, 0}}, 
           {{0.0, 0.0}}, 
           {{0, 0, 0, 0}}, 
           {{0, 0, 0, 0}} }; 

लेकिन ऐसा लगता है कि सभी मुसीबत सरणियों, जो initializer_list के लिए कोई निर्माता मिला है और में निहित है उचित कन्स्ट्रक्टर के साथ रैपिंग सरणी इतना आसान काम नहीं लगता है।

उत्तर

40

प्रारंभकर्ता सूचियां टुपल्स के लिए प्रासंगिक नहीं हैं।

मुझे लगता है कि आप सी ++ 0x में घुंघराले ब्रेसिज़ के दो अलग-अलग उपयोगों को भ्रमित कर रहे हैं।

  1. initializer_list<T> एक सजातीय संग्रह है
  2. Uniform initialization वह जगह है जहाँ कर्ली कोष्ठक आदेश वस्तुओं के सभी प्रकार के निर्माण के लिए उपयोग किया जाता है (सभी सदस्यों, std::tuple के लिए बहुत प्रासंगिक नहीं एक ही प्रकार का होना चाहिए); निर्माणकर्ताओं के साथ सरणी, पीओडी और कक्षाएं। भी the most vexing parse के हल के लिए लाभ)

यहाँ एक सरलीकृत संस्करण है है जो:

std::tuple<int, char> t = { 1, '1' }; 
// error: converting to 'std::tuple<int, char>' from initializer list would use 
// explicit constructor 'std::tuple<_T1, _T2>::tuple(_U1&&, _U2&&) 
// [with _U1 = int, _U2 = char, _T1 = int, _T2 = char]' 

std::tuple<int, char> t { 1, '1' }; // note no assignment 
// OK, but not an initializer list, uniform initialization 

त्रुटि संदेश दर्शाता है कि आप परोक्ष निर्माता कॉल करने के लिए कोशिश कर रहे हैं लेकिन यह इतना आप कर सकते हैं एक स्पष्ट निर्माता है 'टी।

struct A { 
    explicit A(int) {} 
}; 

A a0 = 3; 
// Error: conversion from 'int' to non-scalar type 'A' requested 

A a1 = {3}; 
// Error: converting to 'const A' from initializer list would use 
// explicit constructor 'A::A(int)' 

A a2(3); // OK C++98 style 
A a3{3}; // OK C++0x Uniform initialization 
+0

प्रतिक्रिया के लिए धन्यवाद:

मूल रूप से है कि आप क्या करने की कोशिश कर रहे हैं कुछ इस तरह है! – erjot

+5

ब्रेसिड इनिट सूची के साथ 'std :: tuple' का निर्माण क्यों खराब है? यह 'std :: pair's के लिए काम करता है, और 'std :: tuple'' std :: pair' का सामान्यीकरण है, इसलिए मुझे इस सीमा के कारण को समझ में नहीं आता है: एस ... – rubenvb

+4

@ रूबेनव वर्दी प्रारंभिक (ब्रेसिज़) के साथ 'tuple' प्रारंभ करना ठीक है लेकिन ऐसा करने के लिए आपको बराबर चिह्न छोड़ना होगा। यदि आपके पास बराबर चिह्न है तो इसका मतलब है कि आप प्रारंभिक सूची को स्वीकार करने वाले पैरामीटर कन्स्ट्रक्टर के साथ एक अस्थायी बनाते हैं और फिर अस्थायी मान से कॉपी कन्स्ट्रक्टर का उपयोग करते हैं (हालांकि संकलक इनमें से कुछ को बढ़ा सकता है)। – Motti

संबंधित मुद्दे