Jump to content

List array question


Marioni Unplugged
 Share

You are about to reply to a thread that has been inactive for 3906 days.

Please take a moment to consider if this thread is worth bumping.

Recommended Posts

Lets suppose I have two lists and one integer. The integer can be either  1 or 2. How does one go about it, when I want the value of the integer to determine which list to use in one line, instead of using two if-statements like so:

 

list list1 = ["A","B","C"];
list list2 = ["D","E","F"];
integer int = 1; // or 2
string str;

default
{
    touch_start(integer total_number)
    {
        if (int == 1) str = llLIst2String(list1, 0);
        if (int == 2) str = llLIst2String(list2, 0);    
    }
}

So, in this example str will be either "A" or "D", depending on int, but since LSL doesn't have arrays like list(0) how to do this without the if-statements?

Any suggestions would be appreciated.

 

Marioni

 

 

 

Link to comment
Share on other sites

There's not much advatage to it, but you could combine list1 and list2 to make a strided list and then write

list list12 = ["A","D","B","E","C","F"];integer int1;	integer int2;  // == TRUE || FALSEstring str;default{	touch_start(integer total_number)	{		str = llList2String(list12,int1*2+int2);	}}

 Use int1 to move along the strided list and let int2 (TRUE or FALSE) be the offset that says which stride to choose.  All this does is replace your if tests with assignment statements somewhere else, though.

EDIT:  I left out the *2 multiplier.   Nova got it right (below).  Fixed above. 

Link to comment
Share on other sites

There are no 2 or more dimensional arrays in SL.

There are only strided lists.

There is not much support for strided lists so in this case you need to calculate the index on your own. For your example this means:

list list12 = ["A","D","B","E","C","F"];integer int = 1;string str;default{    touch_start(integer total_number)    {	integer index = 0;        str = llList2String(list12, index*2+int-1);    }}

 I suggest to read here for infos about lists: http://wiki.secondlife.com/wiki/Category:LSL_List

 

Link to comment
Share on other sites

Thanks for your swift reply, I too have thought about merging the two lists. Then, with or without striding, I could let the int variable determine the offset in the list, right? But what worries me, is that you state that it seems to make no difference as to speeding up things.

My script (for a Scrabble game) is now over 50k large and its getting more and more hitching as it grows (e.g. Touch events are skipped). So this question is part of my looking for ways to speed things up. I've narrowed down repetitive code to functions as much as possible already...

Has the strided method no advantage in speed over lots and lots of if-statements at all?

 

Marioni

 

Link to comment
Share on other sites

If there are only two lists, and hence, only one conditional, there's no room for measurable speed advantage.

Something else must underly dropped events. (You do mean touch_start() and/or touch_end(), right? raw touch() events are a stream from which a script can only sample, even if it's doing nothing else.)  Without seeing more of the code, it's hard to guess why events are getting dropped. There aren't any sleeps, right? and no state changes?

On the plus side, combining the two lists into one will save a few bytes, and the code to calculate offsets shouldn't be bulkier, and might even be slightly more compact, than the conditional.

Link to comment
Share on other sites

Yes, I meant touch_start() events. No sleeps, no state changes. Thanks for clarifying touch() events. And yes, compacting and saving bytes is what i've been trying all this time. I will act on upon your, and Rolig's and Nova's advice. Perhaps the dropping of events has another cause indeed.

Much obliged!

 

Link to comment
Share on other sites

I wouldn't concentrate too much on compacting and saving bytes unless you're getting a memory error Your first priority is to get a working script, one that does what you intend it to do. Your second and third priorities (which are nearly as important as the first) is to have the code readable and maintainable. Once you get to that point you can start considering ways to make the code more efficient.

 

I agree with Qie that there is something other than efficiency that is causing dropped events. Perhaps your event queue is overflowing where they are being silently dropped or maybe the conditionals within the event simply aren't being met at times and it appears it wasn't triggered.

 

Figuring why that misbehavior is happening and correcting it should be you main concern right now. Trying for code efficiency now will only delay solving that issue.

Link to comment
Share on other sites

You have talked about a scrabble game .

So , i guess every elements of your lists are only one-char length ?

Maybe your data format is not very adapted :

as the length of your elements are fixed-size , they can be concatenated in a string and accessed easily with the size of the element  

 

list list1 = ["ABC", "DEF"];integer int = 1; // or 2string str;default{    touch_end(integer total_number)    {	str = llGetSubString(llList2String(list1, int-1 ),0,0);       }}

 

Link to comment
Share on other sites

LSL does not have a concept of passing by reference, it puts a whole object on the stack so there is no elegant solution for the list selection. In my own practice when this matter comes up I do something like this:

 

list list1 = ["A","B","C"];list list2 = ["D","E","F"];integer int = 1; // or 2string str;
string getItem(integer listnum)
{
list wlst = list1;
if(listnum == 2) wlst = list2;
return llList2String(wlst,0);
}
default{ touch_start(integer total_number) { str = getItem(int); }}

 

Link to comment
Share on other sites

  • 3 months later...

I also have a question about lists and as long as I cannot start a new thread, I decided to post it here..

I would very much appreciate your help and thank you in advance.. Excuse me for my ignorance... :)

So, here is what I'm trying to do: I retrieve data from an SQL table through llhttprequest. I always read the first 30 rows of the table. Now I want to store this data inside a list (this data is "Questions"). I tried some of the following.. some return a syntax error:

//"listQ" + Index = body;//listQ = llParseString2List(body,["\r\n","\n"],[]);//list newQ = [body];//listQ = listQ + newQ;//integer length = llGetListLength(listQ);//listQ = llListInsertList(listQ, newQ, length);//listQ[index] = newQ;//"listQ" + Index = newQ;//llOwnerSay( (string)newQ );   //listQ[index] = body;

... where "body" is the body of the request and "Index" is the counter for the next request.

The problem is that the list listQ cannot store all 30 questions (in fact it only stores 2 Questions and the third stops in the middle). How can I treat my list as an array? For example, how can I do this...

listQ[index] = body;

 ...or this, in order to have all the 30 records of the table inside listQ...?

"listQ" + Index = body;
Link to comment
Share on other sites

Lists in LSL are immutable; that is, they can't be changed once created.  What you CAN do is create a new list, based on the old one, and assign it back.  To add to a list, for instance:

listQ = listQ + [body];  ('[]' converts the contents to a list, and assuming the body is formatted as you want it.  llStringTrim(body, STRING_TRIM) should be useful).

Conversly, to access an item in a list you need to use a list-access function and assign the data to a variable of the specific type:

string Q10 = llList2String(listQ, 10);   (but note that LSL lists are zero-based so the first question will be in llList2String(listQ, 0))

The wiki is your friend: http://wiki.secondlife.com/wiki/LSL_Portal

[And I don't understand why you can't create a new thread (edit: but now I've read Rolig's answers to your HTTPRequest posts)]

ETA: And LepreKhaun should be along soon to tell you all about JSON arrays in LSL ...

Link to comment
Share on other sites

I have tried this ( listQ = listQ + [body] ), but when i print this listQ, it seems that it only saves the first 3 question that I put in that list. In fact, the third one is cut in the middle, so I figured that the list doesn't have enough space for all 30 questions I want to save...

Is there any way to to save all 30 questions inside one list? Or the only alternative solution is to create 30 different lists foreach one?

Thank you very much for the help...  I'm really confused here... :matte-motes-mad:

Link to comment
Share on other sites

How do you print your list? In a loop line by line or in a single llSay hitting the max length of 1023 for chat commands?

Your script can use max. 64k so thats what limits the length of your list. Since list operations require (at least) one temporary copy of the list that will prevent you from filling up the remaining memory with a single list.

30 questions are no problem though, that will fit easily.

 

If you dont have enough space there are alternatives:

- multiple scripts with sub lists

- store your data on notecards and read just the line you need

- external webserver

 

Link to comment
Share on other sites

Ok I managed to figure out the problem... I was trying to print the list in a single llSay..
By using "string Q10 = llList2String(listQ, 10)"  my problem is solved....!!! So simple.. :smileyfrustrated:

Thanks for the help!

Link to comment
Share on other sites

You are about to reply to a thread that has been inactive for 3906 days.

Please take a moment to consider if this thread is worth bumping.

Please sign in to comment

You will be able to leave a comment after signing in



Sign In Now
 Share

×
×
  • Create New...