Как можно использовать вектор таким образом?

Может кто-нибудь объяснить этот код, пожалуйста? как получается, что функциональная панель принимает ссылку на первый элемент вектора?

jintArray arry;
std::vector<int> foo = GetIntegerArray(env, arry);
bar(&foo[0])

где прототип бара

bar(int* array)

4 ответа

Решение

Это действительно до тех пор, пока тип шаблона не bool, Тип вектора C++ указывает, что векторные элементы являются последовательными в памяти, поэтому вы можете сделать именно это.

Причина, почему это не работает с bool связано со специализацией шаблона. Где bools сжаты до битового поля.

http://en.wikipedia.org/wiki/Vector_%28C%2B%2B%29

как получается, что функциональная панель принимает ссылку на первый элемент вектора?

Это, кажется, источник беспорядка. Выражение &foo[0] это не ссылка на первый элемент, а указатель. operator[] перегружен в vector класс для получения ссылки (или const-reference) и применения & получит адрес объекта.

Да. Просто убедитесь, что вектор не пустой, или &foo[0] было бы ошибкой. C++11 представил std::vector<T>::data() функция, которая не имеет этой проблемы.

Кроме того, возвращать вектор по значению обычно не очень хорошая идея. Возможно, вы захотите использовать выходной итератор или векторный ссылочный параметр в GetIntegerArrayтак вы бы назвали это так:

std::vector<int> foo;
GetIntegerArray(env, arry, back_inserter(foo));

или же

std::vector<int> foo;
GetIntegerArray(env, arry, foo);

Когда вы используете std::vector<int>Гарантируется, что все элементы созданы в непрерывной памяти. Таким образом, когда вы пишете &v[0] он возвращает указатель на первый элемент, и из этого вы можете перейти к следующему элементу, написав &v[0]+1, и так далее.

Кстати, если вы хотите пройти через все элементы или раздел элементов, то лучший интерфейс для bar будет это:

void bar(int *begin, int *end)
{
     for ( ; begin != end; ++begin)
     {
         //code
     }    
}

Таким образом, вы можете позвонить так:

bar(&foo[0], &foo[0] + foo.size());//process all elements
bar(&foo[0], &foo[0] + foo.size()/2);//process first half elements
bar(&foo[0], &foo[0] + N); //process first N elements(assumingN <=foo.size())
bar(&foo[0]+foo.size()/2, &foo[0]+foo.size());//process second half elements
Другие вопросы по тегам