• 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.

Array Indexing problem with handles

Status
Not open for further replies.
Level 14
Joined
Apr 20, 2009
Messages
1,543
Hey all.

I made a little spell that makes use of a timer.
The problem is: I'm executing a function for the timer and I need to exchange some data to this function.

Now I was thinking about creating a global array that stores this data in which the index equals the handle ID of the timer.

However, this is impossible since a handle ID is usually a really long number and the index of an array only goes to 1891.
Now I know what you're thinking: just use a hashtable to store the handle ID in the parent key.

No! I am using a Unit Indexer and would like to keep it that way...
Anyone has any idea on how to tackle this problem?

Is encryption a possible solution? Encrypting the handle ID to make it smaller? What kind of encryption can turn it into a number under 1891 if it is possible?

Should I otherwise create my own counter or..?
 

Dr Super Good

Spell Reviewer
Level 64
Joined
Jan 18, 2005
Messages
27,258
Is encryption a possible solution? Encrypting the handle ID to make it smaller? What kind of encryption can turn it into a number under 1891 if it is possible?
Not possible. Encryption makes data difficult to read, not smaller.

You have 2 choices.
1. Use a hashtable as hashtable indicies have no limit on the number range.
2. Use a hasthable like algorthim to map an integer into an index of an array. A common one is subtracting the handle id by the handle id of null to give a much smaller handle id. Another is to use the modulus opperation to wrap the number into the size of the array.
 
It is known as hashing. The simplest hash for handle ids is:
JASS:
set x[GetHandleId(h) - 0x100000] = 5

Where h is a handle that is allocated on the regular handle stack. (meaning, it is not a texttag, ubersplat, or anything else that has handle ids 0 to 100)

0x100000 is hexadecimal for 1048576. The handle allocation works like a stack. If there are any free handle ids, it will assign the new handle to one of them. If there are no free handle ids, it will assign the new handle the previous id + 1.

Anyway, the key thing to know is that you can use subtraction to get the value within the range of 8191 (not 1891) at decently fast speeds. Note that this may be a bit memory intensive if you start going into the higher array indexes due to the way Warcraft III allocates memory for arrays. [1][2][3] (note: i say "may" because I haven't tested it yet)

I would personally use hashtables, but you can still use the method described above.

Otherwise, your options are to use some timer attachment system. Usually this is easiest with structs.

This tutorial covers a few of your options:
http://www.thehelper.net/threads/jass-timers-and-how-to-pass-data-to-them.106986/
Ignore the H2I part, it is a bit outdated in that respect. You would use GetHandleId instead. However, it goes over a simple struct stack loop. Another option would be to read this tutorial:
http://www.thehelper.net/threads/how-to-use-timers-in-jass.145499/

Good luck!

EDIT: wowee 2 people beat me to the post haha
 
Level 14
Joined
Apr 20, 2009
Messages
1,543
It is known as hashing. The simplest hash for handle ids is:
JASS:
set x[GetHandleId(h) - 0x100000] = 5

Where h is a handle that is allocated on the regular handle stack. (meaning, it is not a texttag, ubersplat, or anything else that has handle ids 0 to 100)

0x100000 is hexadecimal for 1048576. The handle allocation works like a stack. If there are any free handle ids, it will assign the new handle to one of them. If there are no free handle ids, it will assign the new handle the previous id + 1.

Anyway, the key thing to know is that you can use subtraction to get the value within the range of 8191 (not 1891) at decently fast speeds. Note that this may be a bit memory intensive if you start going into the higher array indexes due to the way Warcraft III allocates memory for arrays. [1][2][3] (note: i say "may" because I haven't tested it yet)

I would personally use hashtables, but you can still use the method described above.

Otherwise, your options are to use some timer attachment system. Usually this is easiest with structs.

This tutorial covers a few of your options:
http://www.thehelper.net/threads/jass-timers-and-how-to-pass-data-to-them.106986/
Ignore the H2I part, it is a bit outdated in that respect. You would use GetHandleId instead. However, it goes over a simple struct stack loop. Another option would be to read this tutorial:
http://www.thehelper.net/threads/how-to-use-timers-in-jass.145499/

Good luck!

EDIT: wowee 2 people beat me to the post haha

But yours is more elaborative :)
Thanks so much man, this was exactly what I needed to know!
It's great to learn new things like this I love it :goblin_good_job:
+rep to all of you for helping me out on this!
 
Status
Not open for further replies.
Top