CannibalSmith ([info]cannibalsmith) rakstīja [info]koderi kopienā,
@ 2008-05-07 09:27:00

Previous Entry  Add to memories!  Tell a Friend!  Next Entry
STL iteratori
Kas ir tas minimums klases metožu, kas nepieciešams, lai implementētu ar STL saderīgu uz priekšu ejošu iteratoru, kas lasa un modificē elementus, savai custom datu struktūrai? Gūglē neatradu tiešu un saprotamu atbildi. Mans galvenais mērķis ir spēt izmantot bezgala ērto BOOST_FOREACH.


(Ierakstīt jaunu komentāru)


[info]bubu
2008-05-07 15:31 (saite)
imho tikai divas metodes - begin un end.
Un ja ar to nelīdz, tad šo lasīji? http://www.boost.org/doc/libs/1_35_0/doc/html/foreach/extensibility.html

(Atbildēt uz šo) (Diskusija)


[info]cannibalsmith
2008-05-07 16:27 (saite)
Begin un end implementē pati datu struktūra nevis iterators.

Lasīju, bet vēl negribu padoties.

(Atbildēt uz šo) (Iepriekšējais) (Diskusija)


[info]bubu
2008-05-07 17:26 (saite)
Ah tu to prasīji par iteratora klasi.
Nu tur ir dažādi varianti.
Iteratori ir dažāda veida - forward, bidirectional, random access, input vai output vai abu veida, utt..

Katram no tiem ir noteikts kādām metodēm jābūt definētām.
Piemēram, forward iteratoram ir obligāti jābūt ++ metodie. bidirectional jābūt ++ un --, random access ir jābūt ++, --, + (int N), - (int N), utt. (tās nav vienīgie operatori, kurus es te uzskaitīju).
Reku palasi te: http://www.sgi.com/tech/stl/Iterators.html
Tur ir visai skaidri uzskaitītas visas metodes, kas vajadzīgas.

Papildus tam, iteratoram ir jādefinē tags, kāda tipa iterators tas ir: http://www.sgi.com/tech/stl/iterator_tags.html

(Atbildēt uz šo) (Iepriekšējais) (Diskusija)


[info]cannibalsmith
2008-05-14 09:32 (saite)
Tu pats esi kādreiz veiksmīgi implementējis iteratoru?

(Atbildēt uz šo) (Iepriekšējais) (Diskusija)


[info]bubu
2008-05-14 15:26 (saite)
Kautkad sen sen esmu.

(Atbildēt uz šo) (Iepriekšējais) (Diskusija)


[info]cannibalsmith
2008-05-23 12:40 (saite)
Yeah, baby, yeah! Šitais strādā! Urā! Aleluja! (Paskaidrojums: tas ir orientēts grafs, un iterators to pārmeklē plašumā.)
class Node
{
public:
	template <class T>
	class Iterator : public std::iterator<forward_iterator_tag, Node>
	{
	public:
		Iterator(T* t) { open.push_back(t); }
		Iterator() { }
		Iterator(const Iterator& i) : open(i.open), closed(i.closed) { }
		Iterator& operator =(const Iterator& i) { open = i.open; closed = i.closed; }
		bool operator ==(const Iterator& i) const
		{
			if (!open.empty() && !i.open.empty())
			{
				return open.front() == i.open.front();
			}
			else if (open.empty() && i.open.empty())
			{
				return true;
			}
			else
			{
				return false;
			}
		}
		bool operator !=(const Iterator& i) const { return !(*this == i); }
		T& operator *()
		{
			if (open.empty())
			{
				throw "Iterator cannot be dereferenced.";
			}
			return *open.front();
		}
		operator T&() { return **this; }
		T* operator ->() { return &**this; }
		Iterator& operator ++()
		{
			if (open.empty())
			{
				throw "Iterator cannot be incremented.";
			}
			T* i = open.front();
			open.pop_front();
			FOREACH(T* j, i->children)
			{
				if (find(closed.begin(), closed.end(), j) == closed.end() && find(open.begin(), open.end(), j) == open.end())
				{
					open.push_back(j);
				}
			}
			closed.push_back(i);
			return *this;
		}
		Iterator operator ++(int) { Iterator i(*this); ++*this; return i; }
	protected:
		list<T*> open;
		list<T*> closed;
	};
	typedef Iterator<Node> iterator;
	typedef Iterator<const Node> const_iterator;
	iterator begin() { return iterator(this); }
	iterator end() { return iterator(); }
	const_iterator begin() const { return const_iterator(this); }
	const_iterator end() const { return const_iterator(this); }

	/* [..] */
}

(Atbildēt uz šo) (Iepriekšējais) (Diskusija)


[info]cannibalsmith
2008-05-23 12:42 (saite)
Whoops, ; beigās aizmirsu un pareizi ir const_iterator end() const { return const_iterator(); } .

(Atbildēt uz šo) (Iepriekšējais) (Diskusija)


[info]bubu
2008-05-23 14:24 (saite)
Tev tur bugaina metode:
Iterator& operator =(const Iterator& i) { open = i.open; closed = i.closed; }

Tur vajag return *this;

(Atbildēt uz šo) (Iepriekšējais) (Diskusija)


[info]cannibalsmith
2008-05-23 14:27 (saite)
Paldies!

(Atbildēt uz šo) (Iepriekšējais)


Neesi iežurnalējies. Iežurnalēties?