С++: как построить объект с двумя итераторами?

У меня есть образец большого целочисленного класса. Он содержит динамический массив цифр, составляющих большое целое число. Я хотел бы построить объекты этого класса, используя 2 итератора (начало и конец), чтобы я мог передавать цифры из std::vector или std::list.

Некоторый псевдокод, иллюстрирующий мою идею:

BigInteger(std::iterator begin, std::iterator end);
...

Применение:

std::vector<int> v;
// fill vector with digits
...
BigInteger b(v.begin(), v.end());

Вопрос: как правильно объявить такой конструктор? Тоже даже возможно?

Спасибо!


person nickolay    schedule 15.05.2013    source источник
comment
Так же, как это делает vector: en.cppreference.com/w/cpp/container /вектор/вектор   -  person gha.st    schedule 15.05.2013
comment
Итак, нет возможности использовать какой-то общий тип итератора?   -  person nickolay    schedule 15.05.2013
comment
Нет общего типа итератора. Учтите, что int* является допустимым итератором.   -  person gha.st    schedule 15.05.2013
comment
@DaddyM нет простого способа, потому что нет общего типа итератора. Вы должны были бы создать один. Это, вероятно, не стоит хлопот.   -  person juanchopanza    schedule 15.05.2013
comment
Я предполагаю, что v - это вектор int или что-то подобное.   -  person Martin York    schedule 16.05.2013
comment
@LokiAstari, да. Спасибо. Я починил это.   -  person nickolay    schedule 16.05.2013
comment
@dionadar Ага. Я понимаю, что самый простой итератор — это обычный указатель. Спасибо.   -  person nickolay    schedule 16.05.2013


Ответы (2)


Используйте конструктор шаблонов:

template<class InputIterator>
BigInteger( InputIterator begin, InputIterator end )

Это следует использовать как:

std::vector<int> v; //Fill with values    
BigInteger( v.begin(), v.end() );
person Connor Hollis    schedule 15.05.2013
comment
Итак, нет возможности использовать какой-то общий тип итератора? - person nickolay; 15.05.2013
comment
мне нужно использовать ссылку на итератор вместо того, чтобы просто копировать объект итератора? Будет ли это возможно и эффективнее? - person nickolay; 15.05.2013
comment
Итак, InputIterator — это распространенный тип итератора. Вы можете просто использовать Iterator, если хотите. Ссылка работает, но, по-видимому, обычной практикой является использование итераторов не по ссылке. Проверьте этот ответ: stackoverflow.com/questions/1104035/generic-iterator-in-c - person Connor Hollis; 15.05.2013
comment
Спасибо за ваш опыт. - person nickolay; 16.05.2013

Вы не можете использовать его просто!

Если вы объявите типы итераторов как шаблоны, вы можете получить следующее:

template <typename Itr>
BigInteger(Itr begin, Itr end)
{
}

or

BigInteger(std::vector<int>::iterator begin, std::vector<int>::iterator end)
{
}

Но как насчет std::iterator. Ну, std::iterator - это класс шаблона, и вы должны указать его параметры, и вы должны получить от него

class MyItr : public std::iterator<std::input_iterator_tag, int>
{
...
};

BigInteger(MyItr begin, MyItr end)
{
}

Это долгая история! Возможное определение std::iterator:

  template<typename _Category, typename _Tp, typename _Distance = ptrdiff_t,
           typename _Pointer = _Tp*, typename _Reference = _Tp&>
    struct iterator
    {
      typedef _Category  iterator_category;
      typedef _Tp        value_type;
      typedef _Distance  difference_type;
      typedef _Pointer   pointer;
      typedef _Reference reference;
    };

Как видите, это просто пустой класс с некоторыми typedefs. Итак, вам нужно реализовать operator*(), operator->(), begin(), end(),... для производного итератора.

person masoud    schedule 15.05.2013
comment
скажите, пожалуйста, что я должен реализовать вместо ...? - person nickolay; 16.05.2013
comment
@DaddyM: использование шаблонов для передачи итераторов является обычным и простым способом. std::iterator - это не прямой путь, вам нужно переопределить много членов, это просто пустой класс. - person masoud; 16.05.2013