Is the array object completely broken?

0 favourites
From the Asset Store
This is a single chapter from the "Construct Starter Kit Collection". It is the Student Workbook for its Workshop.
  • Hi,

    I've been using Construct 2 for several years now, but this week I had to deal with the Array object for the first time.

    For some reason, I can't seem to get it to work right. Despite having experience with arrays from several programming languages, I can't seem to do so much as get a simple 3D array up and running without getting strange results or even complete browser freezes.

    I've asked around on IRC and even made a topic containing an example but haven't had much luck getting a response.

    I guess my question is, is the Construct 2 Array object working as it should, allowing you to insert values and iterate through it as you normally would in other languages? Or are there known issues?

    You can check out the above mentioned topic for a specific example.

    Any comments?

  • The definition of coincidence right here. I just decided (like 3 days ago) to create 3D Array Plugin that uses a named convention system (Dynamic Storage) for the exact same reason as working with the array plugin as it is wasn't working the way i would expected it to coming from a traditional programming languages.

    The plugin is still beta but should work the way you expect. I have an example capx that I use for testing each feature that is list below. You should be able to quickly see how it works.

    Heres the plugin

    [attachment=1:3tdmevyv][/attachment:3tdmevyv]

    And heres the example capx i use to test its features as i add them

    [attachment=0:3tdmevyv][/attachment:3tdmevyv]

    A screen shot of what it looks like in use.

    [attachment=2:3tdmevyv][/attachment:3tdmevyv]

    Hopefully this helps

  • Thanks for the response.

    It's great to see that you're doing something about this, but unfortunately I'm coding a rigid engine for a future commercial project, and first and foremost I'd like to try to understand exactly what the issue is here before I decide to move on to third party solutions.

    Do you have any insights into exactly what isn't working with the Construct 2 Array?

  • unfortunately no... I took one look at the array plugin and was "its like time to learn the SDK because this wont work for me" Sure enough the SDK is really easy if you have any JavaScript background (It sounds like you do) you could simply open up the array plugin and see what its doing vs what you'd expect. I have to assume its working the way its intended because im sure there are tons of people using it. It just didn't work the way I expected/wanted it to and I couldn't wrap my head around it i came up with this.

  • I wish I could open up arrays and fill in initial data visually rather than through events, but I rarely have many issues with arrays.

  • The array system is not broken it's just peculiar. I've worked with all 3 depth for it.

    C2 stores the 3D arrays as XYZ.

    X

    Y

    Z.

    X is root.

    Y is the sub of X

    Z is the sub of Y.

    now I'm sure you you already know this. heck I knew this before using C2 and I still had problems getting around C2's array. I still don't like C2 arrays and wish they worked as the variables work. However it doe work and you can work with them. GL though.

  • What is wrong with the arrays? How do people expect them to work?

  • AnD4D

    The way arrays usually work in all programming languages is they are dynamically referable locations of memory. IE. Each level can be accessed by "string" name or variable. Imagine you create function and the first parameter happens to be the name of the dictionary you want to access (Not the key value but that actual dictionary. In C2 this currently not possible with out hard coding all possible dictionary's in advance. So you are limited to only having a single level of dynamic access which are the dictionary keys. (Notice you can dynamically access values in a dictionary but you cannot dynamically access the dictionary its self). This is the limiting factor of C2 where not being able build large complex structures like recursive functions or dynamic data algorithms (closed loop systems) like a game engine or operating system. Its just not possible.

    Using my plugin here is an example of looping through the first level of fields just as if it were a dictionary. This will loop through every key in player 1 and print his attributes. Nothing special becuase dictionarys already support this.

    [attachment=1:38izb030][/attachment:38izb030]

    But lets say I have 2 players and I want the score from each player (Each player would have his own dictionary for this. (this is simple example and I know there are ways of doing this in C2 but look at how simple it is with 2 levels of dynamic access). Instead of some grand method required I can do for each player key and get a list of the same item for each player in a single line of code. This is the power of multilevel dynamic data access and in truth is the foundation of all programming.

    [attachment=0:38izb030][/attachment:38izb030]

    There are so many benifits to this its hard to explain them all but let me give one more screen shot to help prove the point. By keeping all my data in a single location I can also debug problems much faster. Here is a screen shot of the storage container in debug view. Notice how easy it is to keep track of.

    [attachment=2:38izb030][/attachment:38izb030]

    Lastly as the plugin supports pushing and poping data as JSON objects I can send raw JSON strings back and forth via AJAX for communication with my server. And it can so much more. The problem is that since most of the people that use C2 are not traditional developers they have no idea what there missing by not having this crucial fundamental ability that is inherent to programming.

  • troublesum: You might want to "publish" your plugin in the adequate forum.

    As for arrays, manual articles and tutorials are available as to the specificities of C2 and they work very well.

  • troublesum,

    The way arrays usually work in all programming languages is they are dynamically referable locations of memory. IE. Each level can be accessed by "string" name or variable.

    NOPE[/code:1l4lru5h]An array, in traditional programming language (C/C++/C#, Java, Python,...) is a list of contiguous elements of the same size (in memory). No more, no less. 
    When saying "dynamically referable location" you probably mean that you can use a variable that can dynamically change to access any part of the array. And that's right.
    However, you can access each element using an integer index. Not a string, only an integer.
    
    For example, let say we have an array of 4bytes integers.
    In C (let's get back to the bare basics) you would do[code:1l4lru5h] int myArray[10]; //create an array of 10 ints[/code:1l4lru5h]
    This will exactly reserve 4*10 = 40bytes of memory.
    if we were to represent the array in memory, we could imagine something like that:
    [code:1l4lru5h]
    indices :   0    1    2    3    4    5    6    7    8    9
    schema:    [int][int][int][int][int][int][int][int][int][int]
    offsets  :  0    4    8    12   16   20   24   28   32   36   40 ...
    [/code:1l4lru5h]
    So how does an array work its magic?
    when you do myArray[7], the computer knowing that all element have 4bytes will look at the 7x4th byte from the start of the array
    And indeed the int at index 7 is the one at the offset 28 byte.
    
    That's how array works. No more, no less.
    
    Now, there's something that might confuse people depending on how you use arrays in some programming languages.
    
    [h2]Multi-dimensional arrays  ARE NOT array of arrays![/h2]
    
    A Multi-dimensional array is just an arithmetic trick. In memory, it's still a single line of contiguous data. However an Array of Array is an array of pointers to arrays spread over the memory.
    In C, you declare a 2-dimensional array like this:
    [code:1l4lru5h]int multiArray[2][3]; // initialise a 2D array. For clarity let say it has a height of 2 and a width of 3[/code:1l4lru5h]
    here is what it looks like in memory:
    [code:1l4lru5h]
    indices1:   0    0    0    1    1    1  
    indices2:   0    1    2    0    1    2
    schema:    [int][int][int][int][int][int]
    offsets:    0    4    8    12   16   20   24...
    [/code:1l4lru5h]
    if you want a value at index [1][2]  you get the value at offset (indice1 * width + indice2) * size_of_int  = (1 * 3 + 2) * 4 = 5*4 = 20
    
    Now an array of array, in C is declared like this:
    [code:1l4lru5h]int* arrayOfArray[3] // array of pointers to int. Or, for simplicity's sake: array of arrays of ints[/code:1l4lru5h]
    The special character* means pointer to what is before it.
    It means that you don't have an array of ints anymore, but an array of pointers to an int (yeah those iffy pointers is why people don't like C/C++). 
    For this short explanation, you just have to understand that an array of ints is under the hood a pointer to an int (the first of the array then you use the previously mentionned offset to traverse your memory). Then you can understand that as "array of pointers to an int", or more conceptually "array of arrays of ints"
    in memory, it looks like
    [code:1l4lru5h]
    indices :   0     1     2    3    
    schema:    [int*][int*][int*]
    offsets  :  0     4     8    12...
    [/code:1l4lru5h]
    (yeah pointers often also take 4 bytes but it depends on the compiler)
    
    So when you do 
    [code:1l4lru5h]arrayOfArray[2][/code:1l4lru5h]
    You basically get an array of int.
    Obviously C allows you to get any value in this array as well, so you can do something like
    [code:1l4lru5h]arrayOfArray[2][3][/code:1l4lru5h]
    But what happens isn't the same as with the 2D array. Here you don't do arithmetics per se, you directly go to were a second array of int is,  and use it directly like a simple array. A bit like Matryoshka doll  or like following a path.
    
    One of the main differences between the two, in practice, is that the arrays of your array of arrays can have different sizes (jagged arrays). It allows you for example, to build triangular matrices.[code:1l4lru5h][[3,2,1],
     [2,1]
     [1]][/code:1l4lru5h]
    Using a multi-dimensional array, You you just always have the same width, height, depth,...  So it's a good fit for square matrices.[code:1l4lru5h][1, 0, 0,
     0, 1, 0
     0, 0, 1][/code:1l4lru5h]
    
    Small note about javascript:
    Arrays in javascript are very far away from C arrays. They actually aren't really arrays but objects that expose a behavior close to arrays. Nonetheless, you can't access their elements by strings.
    Also, "true" multidimensional array in javascript, and also php are impossible. People talking about multidimensional array in those language are merely refering to how they use it. But make no mistake, they are indeed Array of arrays in all case.
    
    C2 array object aims to emulate the behavior of a true multidimensional array, that's why your can't easily have jagged arrays.
    
    
    

    accessed by "string"

    What you were refering to is called by many names. "Hashtable","Hashmap","Dictionary","Records",...

    [rant]Basically it's a datastructure which allows you to access a value indexed using a hash.

    Well usually, you don't use the hash but something that can be hashed (let say for example,... a string).

    The hash will correspond to an index in an array of "bucket" (another kind of datastructure) which contains all value whose key have the same hash (hash collision).

    The corresponding value is then inserted in or retrieved from this bucket.

    A hashtable is slightly slower than an array. Since read and write require more computation. But it often doesn't matter.[/rant]

    C2 dictionnary is just a simple basic hashtable.

    This is the limiting factor of C2 where not being able build large complex structures like recursive functions or dynamic data algorithms (closed loop systems)

    You can build recursive function in C2.

    + Function: "factorial"
      + Function: parameter 0 <= 1
        -> Function: set return value to 1
      + else
        -> Function: set return value to Function.param(0) * Function.call("factorial",Function.param(0) - 1)[/code:1l4lru5h]
    
    Also, you can build complex datastructure as well with a few hacks, but since it involves passing and parsing JSON strings arround, it's very inefficient.  And yeah there's no easy way to create things like circular linked list. It's not impossible, but it would require building a whole set of function interfaces to access some data a certain ways to simulate memory references. And safe is to say that we would move toward crippling efficiency. C2 is slow enough :D
    
    I would advise to take a look at my [url=https://www.scirra.com/forum/plugin-json-import-export-generate-edit-inspect_t100042]JSON plugin[/url]. It's still in development but I'm using it at work and it simplify few things.
    
    At home I already implemented the hability to load/save objects by reference. So you will be able to create any cyclic datastructure you want. 
    But since I have no cool ways to save that as json for debugging or saving, I'm still looking for a good solution.
  • Try Construct 3

    Develop games in your browser. Powerful, performant & highly capable.

    Try Now Construct 3 users don't see these ads
  • ++What Yann said.

    Arrays are much more fundamental than "collection classes" which is what most people who just started coding in the past 10 years think of when they are talking about lists of things... collection classes provide a lot of convenience features like lookup by field name string or index...etc.

    Attached is the capx from "bolosaur" on his other thread () with changes that use the three dimension array in a manner that might be useful to him... of coarse you can use the C2 Array in many different ways because it isn't a "collection class" but an array with various utility methods added on.

    [attachment=0:r8aknghi][/attachment:r8aknghi]

  • Yann Good lord sir... a simple "well that's kind of true but you meant to say was hash table" i think would have sufficed and even then that's nitpicking considering most C2 users aren't developers. I may as well be on reddit with a response like this. Yes all I did was mask a 3 dimensional JavaScript "object" (technically not an array for those that are in to symantecs) similar to whats available in most high level languages like JavaScript or PHP. That "object" however, which for most developers that program in high level languages, is considered and used like an array (they are practically synonymous even though not technically the same). I want people to use my plugin, not be scared away by complicated technical jargon, so they would have an option for dynamically "string" accessible 3 dimensional information which isn't currently available C2.

    I encourage you to at least try my plug in and offer constructive criticism on it before giving me a hard time for being symanteclly incorrect.

  • Yann Good lord sir...

    I encourage you to at least try my plug in and offer constructive criticism on it before giving me a hard time for being symanteclly incorrect.

    Your plugin looks interesting and would probably be helpful to a lot of people who do not want to dig in and learn how to use the Array.

    I will check it out myself to see how it compares (pros and cons) with the tools I have built for myself on top of the C2 Array.

    With my current method of using the C2 array my column names are C2 instance variables and so they show up in the C2 intellisense and when I change a variable name it goes through all the events and updates the name in all the places where I used that variable... with your plugin is that possible or not because you are referring to everything with strings of text?

  • [quote:1ffx73v9]With my current method of using the C2 array my column names are C2 instance variables and so they show up in the C2 intellisense and when I change a variable name it goes through all the events and updates the name in all the places where I used that variable... with your plugin is that possible or not because you are referring to everything with strings of text?

    Is this what you mean for intellensence? You could have variables with string names that are used for referencing.

    [attachment=1:1ffx73v9][/attachment:1ffx73v9]

    [attachment=0:1ffx73v9][/attachment:1ffx73v9]

  • Yes that is basically what I meant.

    I think this probably just comes down to a convenience vs performance decision... just like in normal programming languages.

    The tools I have built on top of the C2 Array allows me to do basically the same thing you are doing except all through indexes (and arrays of UIDs pointing to more Arrays for hierarchies) instead of string / hash lookups... so I do not do any loops at all which will make it run faster than your plugin will... the con to my tools is it took me months to build them up as I was working on a game before they got to the point where they are today... with your plugin people can get the immediate usefulness of the plugin with the sacrifice of some performance.

    Your tool should probably be used by people to get their game up and going quickly and only switch to something more efficient like indexing via the C2 Array if they need to squeeze out more performance after doing tests.

Jump to:
Active Users
There are 1 visitors browsing this topic (0 users and 1 guests)