SUMMARY: By passing an indexed array (my_array[5] instead of my_array) into a function or native which accepts an array, the index you pass in becomes the base of the array the function you called accepts.
So, if you pass in my_array[5] to my_func, then when my_func does your_array[0], it is the value of my_array[5].
LONGER EXPLANATION:
Code: Select all
public test()
{
new str2[100] = "y halo thar"
test2(str2[2]);
}
// This shows that its not a fluke or a compiler optimization
public test2(str[])
{
test3(str)
}
public test3(str[])
{
// Writes "halo thar" to file
write_file("addons/amxmodx/test.ini",str);
}This is a primitive form of "array slicing", which can be done with any kind of array. It lets you cut out a subset of the array by telling where you want the array to start at when you pass it. True array slicing can do a lot more, but this is the same amount that C affords us natively using pointers, so we can't be picky.
USES:
Why is this useful? Well, for one thing, it can allow us to do a lot of operations without calls to natives. For example, usually when you want a subset of the string, you have to use copyc or format to get it out, therefore using a native call AND allocating a buffer onto the stack (costly due to zeroing).
However, what if you don't REALLY want a new copy; it'd be perfectly fine if the old copy was messed with and mangled, you just don't want the front part? Or, what if you aren't even going to edit the string; you just need to cut a part out? In that case, string slicing is the only real way to do it, unless you want to go to costly natives like format. Here is a peice of code which makes this easy to understand:
Code: Select all
new str_to_cut[] = "Cut us here| Woah important info"
stock testfunc(str[])
{
new i = containi(str,"|")
parse_me(str[i])
}
stock parse_me(str[])
{
// Do stuff on string AFTER pipe
}Obviously, there are better examples; for instance, the one I am quite fond of is for using in set_task. Instead of using explode (costly) or strtok (costly), if we assume we don't really need nor care about keeping the integrity of the string (which is almost always the case; you use parts of the string, then you don't use them again, therefore you can ruinate them all you want) then the string slicing alternative becomes a lot more cost efficient.
Another example is when you wish to stuff non-string data at the beginning of a string, for space or efficiency reasons. In some of my newer code, it is often the case that stuffing a few integer values at the beginning of a string is more portable than enum based structs, and a lot simpler to understand in code; what was perhaps 4 integers and a string being passed into another plugin, saved somewhere, only to be passed back without ever being parsed, is now one array. Quite a lot easier on the eyes.
A full explanation of how string slicing works is attached to this post, if you care to read it; I do not guarantee its validity, as it is quite early in the morning.
