Итератор для двухмерного массива
От: ss_greh  
Дата: 10.02.04 17:01
Оценка:
Как лучше создать subj?
Гуру, посоветуйте!
... << RSDN@Home 1.1.3 beta 1 >>
Re: Итератор для двухмерного массива
От: dims12 http://www.relativity.ru
Дата: 10.02.04 19:11
Оценка:
Здравствуйте, ss_greh, Вы писали:

_>Как лучше создать subj?


Может, лучше иметь дело с одномерным массивом одномерных массивов и все?
Re: Итератор для двухмерного массива
От: v_su Мухосранск  
Дата: 11.02.04 03:25
Оценка:
Здравствуйте, ss_greh, Вы писали:

_>Как лучше создать subj?


Сначала определится с удобным тебе порядком обхода, а потом просто создать и все
... << RSDN@Home 1.1.0 stable >>
Re[2]: Итератор для двухмерного массива
От: ss_greh  
Дата: 11.02.04 10:20
Оценка:
Здравствуйте, v_su, Вы писали:

_>>Как лучше создать subj?

_>Сначала определится с удобным тебе порядком обхода, а потом просто создать и все

С порядком я давно определился
Вопрос в другом: должен ли это быть один итератор, или два — в двух измерениях.
Один — неудобно пользоваться. Как прикажите получить значение из точки 18x34?
Т.е. как получить понятно — но неудобно.

Два — ? Непонятно какой из них разыменовывать и как их получать. Один через другой?
Да и как быть в этом случае с концепцией итераторов как абстракцией указателей?

Или тогда внешний итератор будет итератором итераторов? Короче одни вопросы.
Re[3]: Итератор для двухмерного массива
От: Lloyd Россия  
Дата: 11.02.04 10:24
Оценка:
Здравствуйте, ss_greh, Вы писали:

_>Здравствуйте, v_su, Вы писали:


_>>>Как лучше создать subj?

_>>Сначала определится с удобным тебе порядком обхода, а потом просто создать и все

_>С порядком я давно определился

_>Вопрос в другом: должен ли это быть один итератор, или два — в двух измерениях.
_>Один — неудобно пользоваться. Как прикажите получить значение из точки 18x34?
_>Т.е. как получить понятно — но неудобно.

А зачем это делать при помощи итератора?
Re[3]: Итератор для двухмерного массива
От: v_su Мухосранск  
Дата: 11.02.04 11:10
Оценка:
Здравствуйте, ss_greh, Вы писали:

_>>>Как лучше создать subj?

_>>Сначала определится с удобным тебе порядком обхода, а потом просто создать и все

_>С порядком я давно определился

_>Вопрос в другом: должен ли это быть один итератор, или два — в двух измерениях.
_>Один — неудобно пользоваться. Как прикажите получить значение из точки 18x34?
_>Т.е. как получить понятно — но неудобно.

Итератор это последовательный перебор через ++, а уж эту последовательность можешь задать в его реализации. Если твой итератор перебирает все элементы построчно по возрастанию индекса столбца, то
    iter = arr.my_begin();
    cout << *(iter + 18 * arr.colsize() + 34);
... << RSDN@Home 1.1.0 stable >>
Re[3]: Итератор для двухмерного массива
От: Кодт Россия  
Дата: 11.02.04 12:17
Оценка:
Здравствуйте, ss_greh, Вы писали:

_>Вопрос в другом: должен ли это быть один итератор, или два — в двух измерениях.

_>Один — неудобно пользоваться. Как прикажите получить значение из точки 18x34?
_>Т.е. как получить понятно — но неудобно.

_>Два — ? Непонятно какой из них разыменовывать и как их получать. Один через другой?

_>Да и как быть в этом случае с концепцией итераторов как абстракцией указателей?

_>Или тогда внешний итератор будет итератором итераторов? Короче одни вопросы.


N-мерный массив (гиперкуб) можно рассматривать как 1-мерный массив N-1-мерных срезов, зафиксировав любой индекс.

Срез k-го порядка (k-мерный гиперкуб) определяется N-k фиксированными индексами и k свободными.
Срез 0-го порядка — это отдельный элемент.

Адрес k-го порядка — указывает на соответствующий срез.

Соответственно, итератор k-го порядка — это адрес k-го порядка, в котором определено, какой из фиксированных индексов варьируется.
Домен итераторов k-го порядка — это N-k-1 фиксированных индексов и номер 1 скользящего.

У среза k-го порядка можно взять N-k разных доменов k-1 порядка. Из них "естественным" будет тот, у кого номер свободного индекса наименьший.

Адрес k-го порядка может быть значением N-k разных итераторов.

Эскиз
template<int N, class E>
class hypercube
{
public:
  typedef int dimension; // 0..N
  typedef int range; // -1, 0..+oo
  const range FREEINDEX = -1;

  struct indexvector { range i[N]; }; // -1 значит свободный индекс

  const indexvector& sizes() const;
  E& at(const indexvector& ii) // пофиг константность
  {
    assert(find(ii.i, ii.i+N, FREEINDEX)==ii.i+N); // все индексы связаны
    // выдать элемент
  }

  slice all() { indexvector ii; fill(ii.i, ii.i+N, FREEINDEX); return slice(this, ii); }

  struct slice
  {
    hypercube* hc;
    indexvector ii; // k порядка (т.е. k значений свободны)

    slice(hypercube*, indexvector);

    domain subrange(dimension d) const
    {
      assert(ii[d] == FREEINDEX);
      return domain(*this, d);
    }

    domain superrange(dimension d) const
    {
      assert(ii[d] != FREEINDEX);
      indexvector jj = ii; jj[d] = FREEINDEX;
      return domain(slice(hc, jj), d);
    }

    E& at() const { return hc->at(ii); } // можно только для 0 порядка
  };

  struct domain
  {
    slice sl; // k+1 порядка
    dimension d; // номер скользящего индекса

    domain(slice, dimension);

    iterator begin() const { return iterator it(*this, 0); }
    iterator end() const { return iterator it(*this, sl.hc->sizes()[d]); }
  };

  struct iterator
  {
    slice sl; // k порядка - это уже текущее значение
    dimension d; // номер скользящего индекса

    domain mydomain() const { return sl.superrange(d); }

    iterator& operator++() { ++sl.ii[d]; return *this; }
    iteratot& operator--() { --sl.ii[d]; return *this; }

    slice operator*() const { return sl; }
    slice* operator->() const { return &sl; }
  };
};
Перекуём баги на фичи!
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.