Implementing EachIn type support

BlitzMax Forums/BlitzMax Module Tweaks/Implementing EachIn type support

Lomat(Posted 2005) [#1]
Hi All,

I'm currently developing an Iterator module (wb.iterator more info available at BlitzWiki) and was wondering if there was a way to use EachIn for non BRL types.

I have tried to implement an ObjectEnumerator method in my types that functions like the methods found on the TList and TMap objects but this has failed to work so any ideas or suggestions are welcome.

If this is not currently implementable then can I please request such functionality. :)


GW(Posted 2005) [#2]
I think the tLink type is what your after. The docs talk about how you can make your own type handle iteration like a linked list.


Lomat(Posted 2005) [#3]
GW:

I dont think thats what i'm after as the TLink type is just that, a link. Its only purpose is to be a specific link within a list.

You can use the EachIn keywork with both arrays and tMap objects and none of those use the TLink type so there must be some other kind of magic happening.

I know that i could turn my Iterator objects into linked lists and then use the EachIn keyword to iterate over the resulting linked list but tbh that is a complete waste of both time and resources :)


Robert(Posted 2005) [#4]
I have tried to implement an ObjectEnumerator method in my types that functions like the methods found on the TList and TMap objects but this has failed to work so any ideas or suggestions are welcome.


I suggest that you browse the code in the BRL.List module. I cannot remember the exact details of how iterators work, but IIRC it does involve the ObjectEnumerator method.


Cajun17(Posted 2005) [#5]
Here's a quick example of a user type implementing for/eachin ability.

Framework BRL.basic

Type Datum
	Field num:Int
EndType

Type Collection
	Field somedata:Datum[]
	
	Method startup()
		For Local i:Int = 0 To 20
			somedata = somedata[..i+1]
			somedata[i] = New Datum
			somedata[i].num = i * i
		Next
	EndMethod
	
        'this method is placed within the collection you want to loop through
	Method ObjectEnumerator:CollectionIterator()
		Return CollectionIterator.Create(Self)
	EndMethod
	
End Type

'this is your iterator, it needs to have these 2 methods
'it also has to somehow keep track of where it is in the list
'the create function is only for simplicity
Type CollectionIterator
	Field aCollection:Collection
	Field index:Int

	Method HasNext:Int()
		Return (index < aCollection.somedata.length)
	EndMethod
	
	Method NextObject:Object()
		index:+1
		Return(aCollection.somedata[index - 1])
	EndMethod
	
	Function Create:CollectionIterator(c:Collection)
		Local t:CollectionIterator = New CollectionIterator
		t.index = 0
		t.aCollection = c
		Return t
	EndFunction
EndType


Local cc:Collection = New Collection
cc.startup()

For Local iter:Datum = EachIn cc
	Print iter.num
Next



Lomat(Posted 2005) [#6]
Thanks guys.

I must have done something really, err well, stupid when i tried to implement the ObjectEnumerator method before but i've got it working now so can release an updated version of the module :)