2010-04-22 16 views
14

Estoy tratando de entender el boost array. El code se puede leer fácilmente desde el sitio del autor.¿Cómo debo inicializar un boost :: array?

En la lógica de diseño, el autor (Nicolai M. Josuttis) mencionó que los siguientes dos tipos de inicialización son posibles.

boost::array<int,4> a = { { 1, 2, 3 } }; // Line 1 
boost::array<int,4> a = { 1, 2, 3 };  // Line 2 

En mi experimento con g ++ (versión 4.1.2) La línea 1 está funcionando pero la línea 2 no lo está. (Línea 2 se obtiene la siguiente:

warning: missing braces around initializer for 'int [4]' 
warning: missing initializer for member 'boost::array<int, 4ul>::elems' 

)

Sin embargo, mi principal pregunta es, ¿cómo Línea 1 está funcionando? Traté de escribir una clase similar a array.hpp y utilizar declaración como Línea 1, pero que no funcionó :-(. El error es

typedef array< unsigned int, 10 > MyArray; 

MyArray b = { { 1, 2, 3 } }; // Line 74 

array_test.cpp:74: error: in C++98 'b' must be initialized by constructor, not by '{...}' 
array_test.cpp:74: error: no matching function for call to 'array<unsigned int, 10u>::array(<brace-enclosed initializer list>)' 
array.h:16: note: candidates are: array<unsigned int, 10u>::array() 
array.h:16: note:     array<unsigned int, 10u>::array(const array<unsigned int, 10u>&) 

Puede alguien explicar? ¿Hay alguna cosa específica impulso sucede en Línea 1 que necesito ser consciente de?

+0

Como Potatoswatter menciona esto sólo funciona para POD tipos. Sin embargo, es probable que valga la pena señalar que la próxima especificación de C++ 0x proporciona formas de soporte para listas de inicializadores con tipos que no son de pod. –

+3

es probable que tenga un constructor o campos privados en su clase – Anycorn

+0

+ 1 @aaa: Muchas gracias. Sí, mi matriz (los datos) era privada en mi clase. – Arun

Respuesta

20

esta es una lista abrazadera inicialización regular:

array Boost se define así:

struct array { T elems[N]; }; 

abrazadera interior es para elems matriz de inicialización, Brace outear es para la inicialización struct. Si usted proporciona su propio constructor, que ya no tiene edad, tipo de datos sin formato alguno no puede inicializar el uso de ortesis

aviso de que se puede ir sin llave externa, pero obtendrá una advertencia

+0

+1: Gracias por la explicación de la llave interna y la abrazadera externa. – Arun

+0

Estoy aceptando esto porque esta respuesta junto con el comentario del mismo autor en contra de la pregunta realmente me ayudó a resolver mi problema. – Arun

9

la sección pertinente de la norma es §8.5.1, agregados.

  1. un agregado es una matriz o una clase (cláusula 9) sin declarados por el usuario constructores (12.1), no privados o miembros pro tegido no estáticos de datos (cláusula 11), no hay clases base (cláusula 10), y no hay funciones virtuales (10.3).
  2. Cuando se inicializa un agregado el inicializador puede contener un inicializador-cláusula que consiste en una lista separada por comas brace- cerrado, de inicializador-cláusulas para los miembros del agregado, escrito en creciente subíndice o miembro de la orden . Si el agregado contiene subagregados, esta regla se aplica de forma recursiva a los miembros de la subagregado.

GCC 4.1.2 puede estar violando párrafo 11.

11 Braces puede elididas en un inicializador-lista como sigue. Si la lista de inicializadores comienza con una llave a la izquierda , la siguiente lista de inicializadores separados por comas inicializa los miembros de un subaggregado ; es erróneo que haya más inicializadores que miembros. Sin embargo, si la lista de inicializadores para un subaggregado no comienza con un paréntesis izquierdo, entonces se utilizan inicializadores suficientes de la lista para inicializar los miembros de el subaggregado; cualquier inicializador restante se deja para inicializar el siguiente miembro del agregado de que el subaggregado actual es un miembro .

+0

+1: Gracias por la cotización relevante. – Arun

Cuestiones relacionadas