• Listen to a special audio message from Bill Roper to the Hive Workshop community (Bill is a former Vice President of Blizzard Entertainment, Producer, Designer, Musician, Voice Actor) 🔗Click here to hear his message!
  • Read Evilhog's interview with Gregory Alper, the original composer of the music for WarCraft: Orcs & Humans 🔗Click here to read the full interview.

[Snippet] RecycleStack

Hey guys,

since I am already in Stack-spree, here is my latest idea, a Stack for recycling handles.

JASS:
// ---------------------------------------------------------------------------------------------------------------------------
//
//  RecycleStack
//  ===========
//
//     Version:    1.0.0
//     Author:     Anachron
//
//     Requirements:
//         Stack [by Anachron]
//         (New) Table [by Bribe] (v. 3.1)
//
//     Description:
//         RecycleStack is a way how to create recycleable handle containers
//         that give you the ability to store and recycle handles whenever needed.
//         Useful for dummy systems (casters/spell effects).
//
//     History:
//         1.0.0: Initial Release
//
//     API:
//         thistype.reuse()             --> Use any of the idle handles
//         thistype.recycle(handle x)   --> Put the handle into the recycle bin 
//         thistype.empty()             --> Clear all saved handles
//         thistype.clean(handle x)     --> If existing, you can put here that cleans handles
//
// ---------------------------------------------------------------------------------------------------------------------------
library RecycleStack requires Stack, Table

	//! textmacro CreateRecycleStack takes NAME, TYPE
	private module Init$NAME$RecycleStack
		private static method onInit takes nothing returns nothing
			set thistype.Index = Stack.create()
			set thistype.RecycleBin = Table.create()
		endmethod
	endmodule
	
	module Is$NAME$RecycleStack
		private static Stack RecycleIndex = 0
		private static Table RecycleBin = 0
		
		implement Init$NAME$RecycleStack
		
		public static method reuse takes nothing returns $TYPE$
			local integer recycleId = thistype.RecycleIndex.getLast()
			local $TYPE$ recycleHandle = thistype.RecycleBin.$TYPE$[recycleId]
		
			if recycleHandle == null then
				return null
			endif
			
			call thistype.RecycleIndex.delete(toRecycle)
			call thistype.RecycleBin.remove(recycleId)
			
			static if thistype.clean.exists then
				call thistype.clean(recycleHandle)
			endif
			
			return recycleHandle
		endmethod
		
		public static method recycle takes $TYPE$ toRecycle returns boolean
			local integer recycleId = GetHandleId(toRecycle)
		
			if thistype.RecycleBin.has(recycleId) or toRecycle == null then
				return false
			endif
			
			call thistype.RecycleIndex.add(recycleId)
			set thistype.RecycleBin.$TYPE$[recycleId] = toRecycle
			
			return true
		endmethod
		
		public static method empty takes nothing returns nothing
			loop
				exitwhen thistype.reuse() == null
			endloop
		endmethod
	endmodule
	
	struct $NAME$RecycleStack
		implement Is$NAME$RecycleStack
	endstruct
	//! endtextmacro

Example
JASS:
	//! runtextmacro CreateRecycleStack("Unit", "unit")
	
	private function test takes nothing returns nothing
		set UnitRecycleStack unitBin = UnitRecycleStack.create()
		local unit recycledUnit = null
		
		call unitBin.recycle(CreateUnit(Player(0), 'hpea', 0., 0., 0.))
		call unitBin.recycle(CreateUnit(Player(0), 'hpea', 0., 0., 0.))
		call unitBin.recycle(CreateUnit(Player(0), 'hpea', 0., 0., 0.))
		call unitBin.recycle(CreateUnit(Player(0), 'hpea', 0., 0., 0.))
		call unitBin.recycle(CreateUnit(Player(0), 'hpea', 0., 0., 0.))
		
		loop
			set recycledUnit = unitBin.reuse()
			exitwhen recycledUnit == null
			call SetUnitState(recycledUnit, UNIT_STATE_LIFE, 123.456)
		endloop
	endfunction
 
Last edited:
Level 19
Joined
Mar 18, 2012
Messages
1,716
Assuming Stack ( approved ) is working, this would also work as intended.

Anarchon is inactive and I really don't have an opinion if this is useful or not.

I agree with TriggerHappy on type-to-type recycling.

In general we do not just recycle handles. There is always a deeper purpose:
a) units --> Projectiles, effects, ... but those snippets will deal with handle recycling internally
b) timers --> want to attach data
c) maybe groups

For those I mentioned exists pretty neat code snippets like TimerUtils, MissileRecycler or Dummy, ...
Those do not rely on ReycleStack and will never do.
RecycleStack may turns out to be useful, if you want to code all of these by yourself.

Anyone want to defend the purpose of this resource?
 
Top