Structure in a Structure

TUTechTUTech Junior MemberPosts: 70
Still working on P2 Practical. I was told in another post that it's ok to ask for help.

This will compile, but I get an error C10571 Converting type [string] to [CHAR]. I don't see where I'm converting.
DEFINE_TYPE

STRUCTURE sLightInfo
{
INTEGER nIntensity
INTEGER nFadeTime
}

STRUCTURE sScene
{
char cSName
sLightInfo Lt_Zone1
sLightInfo Lt_Zone2
sLightInfo Lt_Zone3
sLightInfo Lt_Zone4
}

DEFINE_VARIABLE

sScene Preset[3]

Define_Start

Preset[1].cSName = 'Scene1';
Preset[1].Lt_Zone1.nIntensity = 50;
Preset[1].Lt_Zone1.nFadeTime = 3;
Preset[1].Lt_Zone2.nIntensity = 50;
Preset[1].Lt_Zone2.nFadeTime = 3;
Preset[1].Lt_Zone3.nIntensity = 50;
Preset[1].Lt_Zone3.nFadeTime = 3;
Preset[1].Lt_Zone4.nIntensity = 50;
Preset[1].Lt_Zone4.nFadeTime = 3;
Preset[2].cSName = 'Scene2';
Preset[2].Lt_Zone1.nIntensity = 50;
Preset[2].Lt_Zone1.nFadeTime = 3;
Preset[2].Lt_Zone2.nIntensity = 50;
Preset[2].Lt_Zone2.nFadeTime = 3;
Preset[2].Lt_Zone3.nIntensity = 30;
Preset[2].Lt_Zone3.nFadeTime = 3;
Preset[2].Lt_Zone4.nIntensity = 30;
Preset[2].Lt_Zone4.nFadeTime = 3;
Preset[3].cSName = 'Scene3';
Preset[3].Lt_Zone1.nIntensity = 100;
Preset[3].Lt_Zone1.nFadeTime = 3;
Preset[3].Lt_Zone2.nIntensity = 100;
Preset[3].Lt_Zone2.nFadeTime = 3;
Preset[3].Lt_Zone3.nIntensity = 100;
Preset[3].Lt_Zone3.nFadeTime = 3;
Preset[3].Lt_Zone4.nIntensity = 100;
Preset[3].Lt_Zone4.nFadeTime = 3;

The initialization should go in the ONLINE statement but I put it in Start to make sure it will compile first.

Comments

  • TUTechTUTech Junior Member Posts: 70
    I tried this and it wouldn't compile.

    DEFINE_TYPE

    STRUCTURE sLightInfo
    {
    INTEGER nIntensity
    INTEGER nFadeTime
    }

    STRUCTURE sScene
    {
    char cSName
    sLightInfo Lt_Zone
    }

    DEFINE_VARIABLE

    sScene Preset[3]

    Define_Start

    Preset[1].cSName = 'Scene1';
    Preset[1].Lt_Zone[1].nIntensity = 50;
    Preset[1].Lt_Zone[1].nFadeTime = 3;
    Preset[1].Lt_Zone[2].nIntensity = 50;
    Preset[1].Lt_Zone[2].nFadeTime = 3;
    Preset[1].Lt_Zone[3].nIntensity = 50;
    Preset[1].Lt_Zone[3].nFadeTime = 3;
    Preset[1].Lt_Zone[4].nIntensity = 50;
    Preset[1].Lt_Zone[4].nFadeTime = 3;
    Preset[2].cSName = 'Scene2';
    Preset[2].Lt_Zone[1].nIntensity = 50;
    Preset[2].Lt_Zone[1].nFadeTime = 3;
    Preset[2].Lt_Zone[2].nIntensity = 50;
    Preset[2].Lt_Zone[2].nFadeTime = 3;
    Preset[2].Lt_Zone[3].nIntensity = 30;
    Preset[2].Lt_Zone[3].nFadeTime = 3;
    Preset[2].Lt_Zone[4].nIntensity = 30;
    Preset[2].Lt_Zone[4].nFadeTime = 3;
    Preset[3].cSName = 'Scene3';
    Preset[3].Lt_Zone[1].nIntensity = 100;
    Preset[3].Lt_Zone[1].nFadeTime = 3;
    Preset[3].Lt_Zone[2].nIntensity = 100;
    Preset[3].Lt_Zone[2].nFadeTime = 3;
    Preset[3].Lt_Zone[3].nIntensity = 100;
    Preset[3].Lt_Zone[3].nFadeTime = 3;
    Preset[3].Lt_Zone[4].nIntensity = 100;
    Preset[3].Lt_Zone[4].nFadeTime = 3;
  • TonyAngeloTonyAngelo Code Monkey Posts: 315
    STRUCTURE sScene
    {
    char cSName[CONSTANT_REPRESENTING_MAX_LENGTH_OF_STRING]
    sLightInfo Lt_Zone[CONSTANT_REPRESENTING_NUMBER_OF_ZONES]
    }
    
  • TUTechTUTech Junior Member Posts: 70
    I REALLY thought I tried that. I must have fixed that and changed something else at the same time and created another problem while fixing the other. Now it works!
  • ericmedleyericmedley Senior Member - 3709 Posts Posts: 4,141
    I think I've gotten it to work by using two sets of DEFINE_VARIABLE and DEF_TYpe. It's like you have to establish the inner-nested struct as a variable first.

    so, using your variable/structure format:
    DEFINE_TYPE
    
    STRUCTURE sLightInfo
    {
    INTEGER nIntensity
    INTEGER nFadeTime
    }
    
    DEFINE_VARIABLE
    volatile sLightInfo  Lt_Zone1
    volatile sLightInfo  Lt_Zone2
    volatile sLightInfo  Lt_Zone3
    volatile sLightInfo  Lt_Zone4
    
    DEFINE_TYPE
    
    STRUCTURE sScenepp
    {
    char cSName
    Lt_Zone1
    Lt_Zone2
    Lt_Zone3
    Lt_Zone4
    }
    
    DEFINE_VARIABLE
    
    sScene Preset[3]
    

    EDITED TO ADD: I just copy/pasted this into NS and it does indeed compile.
  • a_riot42a_riot42 AMX Wizard Posts: 1,619
    Its not relevant to your task but using structures inside structures is really slow. I wrote a module for a media server, and used the structure in structure format, and couldn't understand why accessing the data was so slow. I changed it all to arrays and it sped things up by an order of magnitude. Its not critical for most things, but if you are populating rows on a touch panels with text data from a structure in structure, you'll notice it. I use structures only for data that that doesn't get heavy read/writes, and use arrays for data that does.
    Paul
  • JasonSJasonS If I had known it was going to be that kind of party... Posts: 227
    I use nested structures all the time and have no issues with speed. You need to make sure that you always define your variables as VOLATILE. The other thing that speeds things up is to use STACK_VAR whenever possible.
  • fogled@mizzou[email protected] h4x354x0r Posts: 547
    I use structures inside structures all the time. I basically build a small relational database with structures to store all the room, device, input, audio, lighting, and other data. But it's my understanding you can only go 5 levels deep with structures before it stops working. I've never really noticed any speed problems with my structures, but don't think I have much if any "heavy read/write" operations in my code. Only one place in my code I'm populating 15 button texts with dynamic data from a 2-deep structure, only when a panel comes online.
  • MLaletasMLaletas Junior Member Posts: 219
    Yea ive only gone two deep with structures, didnt notice any speed problems but I dont believe I was using it for quick status updates or anything that would be effected in a short amount of time.
  • fogled@mizzou[email protected] h4x354x0r Posts: 547
    Also, if the memory footprint of the structures gets to big, it blows everything out of the water. The code compiles and uploads just fine, it just won't run on the controller. I tried implementing a non-volatile error notification tracking structure so controller chatter survived a power cycle for problem analysis & debugging purposes, but... had to take it back out.
  • MLaletasMLaletas Junior Member Posts: 219
    And you cant modify the values in debug with larger structs either which sucks.
  • TUTechTUTech Junior Member Posts: 70
    I really don't see the sense in using a structure for this purpose. I can write four lines of code for each preset and be done.
  • ericmedleyericmedley Senior Member - 3709 Posts Posts: 4,141
    TUTech wrote: »
    I really don't see the sense in using a structure for this purpose. I can write four lines of code for each preset and be done.

    I tend to use structures if the data I'm referring to is stored in some kind of XML-ish way. For example: if I happen to be writing everything to/from the Netlinx "Disk" or if I'm pushing/pulling from an SQL database or something. To my eye, structures kind of have that same feel and writing code to move the data to/from the structure and the database is easy to read and write code.

    I don't think I've every nested a structure for any other reason.

    Also, it may well be that the OP's example is just that: an example for the sake of the discussion. Who knows. But, I too wouldn't do it this way either.
  • TUTechTUTech Junior Member Posts: 70
    ericmedley wrote: »

    I tend to use structures if the data I'm referring to is stored in some kind of XML-ish way. For example: if I happen to be writing everything to/from the Netlinx "Disk" or if I'm pushing/pulling from an SQL database or something. To my eye, structures kind of have that same feel and writing code to move the data to/from the structure and the database is easy to read and write code.

    I don't think I've every nested a structure for any other reason.

    Also, it may well be that the OP's example is just that: an example for the sake of the discussion. Who knows. But, I too wouldn't do it this way either.

    For that use it makes sense.
  • MLaletasMLaletas Junior Member Posts: 219
    For me its pretty typical for my projects to have at least one nested structure. In my framework I have a room structure array in case I am doing a divisible/combinable room or multiple rooms off of one processor. Within that structure array I'll have another structure array nested for all sources for that room which will have all that data for that source (control method, inputs, outputs, name, etc....).
  • fogled@mizzou[email protected] h4x354x0r Posts: 547
    MLaletas wrote: »
    In my framework I have a room structure array in case I am doing a divisible/combinable room or multiple rooms off of one processor. Within that structure array I'll have another structure array nested for all sources for that room which will have all that data for that source (control method, inputs, outputs, name, etc....).
    That sounds nearly identical to the way I use structures. I use them for virtually all data storage in the controller. I've got all the data for up to 25 rooms, 7 devices per room, 5 inputs per room, 5 audio channels per room, stored and running in structures in controllers. I store device API's and value maps in structures too. I totally believe using structures like this seriously bogs down the controller in a way using arrays doesn't; I just haven't yet hit that wall of having that bog-down substantially affect the function of my projects. Yet. I'll get there someday ;-)

  • JasonSJasonS If I had known it was going to be that kind of party... Posts: 227
    I don't see how structures would be any slower than multi-dimensional arrays, as both are pointers to memory locations. The only time that I have seen any noticeable delay doing anything with an NI processor was an alphabetic bubble sort of a contact list of a couple hundred contacts and doing SHA256 encryption. Accessing elements in a structure array just doesn't take long enough to notice. Even a sequential search on a structure array of 50 items is inconsequential.

    One of the really handy things you can do with a structure is pass an element of it as a parameter to a function.

    Another great thing you can do is Variable_to_string on a structure to write it to disk and string_to_variable to read it from disk into a variable in a couple lines of code. The thing that you have to remember here is that NetLinx does not automatically set array lengths on any arrays other than strings (and only when you set the whole string). So you need to manually set array lengths before calling variable_to_string. I tried variable_to_xml in the past but it was unable to encode nested structures. I have even used variable_to_string to send structures into modules using SEND_COMMAND and/or SEND_STRING. I tried it as an experiment and was pleasantly surprised by how quick and reliable it was. I have production code that uses this methodology.
  • ericmedleyericmedley Senior Member - 3709 Posts Posts: 4,141
    JasonS wrote: »
    I don't see how structures would be any slower than multi-dimensional arrays, as both are pointers to memory locations. The only time that I have seen any noticeable delay doing anything with an NI processor was an alphabetic bubble sort of a contact list of a couple hundred contacts and doing SHA256 encryption. Accessing elements in a structure array just doesn't take long enough to notice. Even a sequential search on a structure array of 50 items is inconsequential.

    One of the really handy things you can do with a structure is pass an element of it as a parameter to a function.

    Another great thing you can do is Variable_to_string on a structure to write it to disk and string_to_variable to read it from disk into a variable in a couple lines of code. The thing that you have to remember here is that NetLinx does not automatically set array lengths on any arrays other than strings (and only when you set the whole string). So you need to manually set array lengths before calling variable_to_string. I tried variable_to_xml in the past but it was unable to encode nested structures. I have even used variable_to_string to send structures into modules using SEND_COMMAND and/or SEND_STRING. I tried it as an experiment and was pleasantly surprised by how quick and reliable it was. I have production code that uses this methodology.

    This might be a good topic to bring up with the folks at AMX in NX Firmware. The whole notion of data structs comes from our friends out there in Object-oriented land. In that realm, the advantage of structures is that they can be 'ragged' where a simple multi-dimensional array cannot. Plus, they just look and feel like Object-oriented stuff. with a struct the inner parts are referred to by human-readable names. In a mult-dimensional array you kind of have to remember what the column s and rows represent and its entirely possible to get the wrong.

    I don't know for a fact but I think Netlinx cannot be ragged. A sturct of X dimensions and Y cells takes up the same mem space as an equal array. Also, I've never really seen any noticeable degradation of speed using either method. I typically try to write code not necessarily for it's logical ellegance but more towards efficiency of processor time. But, I will say I choose between MD Arrays vs. Stucts simply for the looks.
  • MLaletasMLaletas Junior Member Posts: 219
    Curious Eric,

    Just because in a struct you can mix and match different data type you want, using MD arrays youll need to make per data type. Is that still a trade off that you accept?
  • a_riot42a_riot42 AMX Wizard Posts: 1,619
    JasonS wrote: »
    I don't see how structures would be any slower than multi-dimensional arrays, as both are pointers to memory locations. The only time that I have seen any noticeable delay doing anything with an NI processor was an alphabetic bubble sort of a contact list of a couple hundred contacts and doing SHA256 encryption. Accessing elements in a structure array just doesn't take long enough to notice. Even a sequential search on a structure array of 50 items is inconsequential.

    One of the really handy things you can do with a structure is pass an element of it as a parameter to a function.

    Another great thing you can do is Variable_to_string on a structure to write it to disk and string_to_variable to read it from disk into a variable in a couple lines of code. The thing that you have to remember here is that NetLinx does not automatically set array lengths on any arrays other than strings (and only when you set the whole string). So you need to manually set array lengths before calling variable_to_string. I tried variable_to_xml in the past but it was unable to encode nested structures. I have even used variable_to_string to send structures into modules using SEND_COMMAND and/or SEND_STRING. I tried it as an experiment and was pleasantly surprised by how quick and reliable it was. I have production code that uses this methodology.

    It depends on the compiler and the memory management. Some systems pad memory when using structs so that the struct takes up a defined space, others store it as is so it takes longer to read. But a large struct with large char arrays inside another struct, will slow things down when compared to nonencapsulated structs doing the same thing. I was parsing HTTP packets, writing to structs within a struct with the appropriate data, and then reading the data to populate buttons on touch panels. It was too slow to be usable. Since I had written so much code already, I figured I'd give it one last shot and remove the struct within a struct method and break them out into nonencapsulated structs and see if it made any difference. It took it from unusable to usable. Here is one struct I used. I had some of these fields in other structs and put them inside this one, but then broke it out so no struct within a struct was needed:
    structure _stAVTransport
    {
        integer        bAlarmIncludeLinkedZones
        char             sAlarmState[32]
        integer        iAlarmVolume
        integer        bEnqueueAsNext
        char            sGroupID[8]
        integer        iInstanceID
        char            sISO8601Time[16]
        char            sMemberID[16]
        char            sMemberList[16]
        integer        iNumTracks
        char            sObjectID[8]
        char            sQueue[8]
        integer        bResumePlayback
        char            sSavedQueueTitle[8]
    
        integer     iAbsoluteCounterPosition
        char             sAbsoluteTimePosition[16]
        integer     iAlarmIDRunning
        char             sAlarmLoggedStartTime[16]
        integer        bAlarmRunning
        char            sAVTransportURI[128]
        char            sAVTransportURIMetaData[128]
        char            sCurrentMediaDuration[16]
        char            sCurrentPlayMode[16]
        char            sCurrentRecordQualityMode[16]
        integer        iCurrentSection
        integer        iCurrentTrack
        char            sCurrentTrackDuration[16]
        integer   iCurrentTrackDuration
        char            sCurrentTrackMetaData[256]
        char            sCurrentTrackURI[256]
        char            sCurrentTransportActions[16]
        char             sLastChange[128]
        char             sNextAVTransportURI[128]
        char             sNextAVTransportURIMetaData[256]
        integer     iNumberOfTracks
        char             sPlaybackStorageMedium[16]
        char             sPossiblePlaybackStorageMedia[16]
        char             sPossibleRecordQualityModes[16]
        char             sPossibleRecordStorageMedia[16]
        char             sRecordMediumWriteStatus[16]
        char             sRecordStorageMedium[16]
        integer        iRelativeTimePosition
        char             sRelativeTimePosition[16]
        integer        bRestartPending
        integer        iSleepTimerGeneration
        integer        bSnoozeRunning
        char            sTransportErrorCondition[128]
        char            sTransportErrorURI[128]
        char            sTransportPlaySpeed[1]
        char            sTransportState[16]
        char            sTransportStatus[16]
    }
    
    Paul
  • JasonSJasonS If I had known it was going to be that kind of party... Posts: 227
    Is the variable declared as an array and is it volatile? I am curious because I have not personally run into any noticeable delay using structures. It could be that I have not used any that were large enough to cause an issue.
  • a_riot42a_riot42 AMX Wizard Posts: 1,619
    Yes it is a struct array and is volatile, but that wasn't the difference, it was the nesting of structs. I think I will test it again since I haven't since the NX series came out. Perhaps they do memory management better, but I doubt it. Having struct within structs would be a nice feature for doing object-oriented type stuff (too bad we can't use pointers to functions as well) but there appears to be a limit how deep you can nest them which is rather odd. You should be able to nest them indefinitely theoretically. Then you could have a Project struct which holds a House struct in which Room structs live, with a TV struct, Lighting struct, HVAC struct inside the Room structs etc all nested. As long as you have access to the Project struct, you have access to every variable in the system. It may be a very slow system though and you'd end with code that looks like this:

    Project[Houses[Rooms[TVs[TV[input].iCurrentInput]]]] = cnHDMI

    All that pointer following comes at a cost.

    Here is what GNU says about the GCC compiler: [h=4]2.4.5 Size of Structures[/h] The size of a structure type is equal to the sum of the size of all of its members, possibly including padding to cause the structure type to align to a particular byte boundary. The details vary depending on your computer platform, but it would not be atypical to see structures padded to align on four- or eight-byte boundaries. This is done in order to speed up memory accesses of instances of the structure type.

    As a GNU extension, GCC allows structures with no members. Such structures have zero size.

    If you wish to explicitly omit padding from your structure types (which may, in turn, decrease the speed of structure memory accesses), then GCC provides multiple methods of turning packing off. The quick and easy method is to use the -fpack-struct compiler option. For more details on omitting packing, please see the GCC manual which corresponds to your version of the compiler.

    I don't know if the AMX compiler pads structs or not. Nested structs and recursion are two things I stay away from when writing Netkinx code.
    Paul
  • TUTechTUTech Junior Member Posts: 70
    So...After I built the structure and initialized it, to active a preset, Button_Event...Push:

    Send_String dvLights,"'FADEDIM,'itoa(Preset[1].Lt_Zone1.nIntensity),','itoa(Preset[1].Lt_Zone1.nFadeTime),',','0[1:1]',$0D"

    That works, but it seems like a really long way to do it?
  • viningvining X Member Posts: 4,346
    The biggest problem I have with structures is debugging, in large nested structs open in debug it often drops offline. Very annoying but I still prefer to use them
  • ericmedleyericmedley Senior Member - 3709 Posts Posts: 4,141
    TUTech wrote: »
    So...After I built the structure and initialized it, to active a preset, Button_Event...Push:

    Send_String dvLights,"'FADEDIM,'itoa(Preset[1].Lt_Zone1.nIntensity),','itoa(Preset[1].Lt_Zone1.nFadeTime),',','0[1:1]',$0D"

    That works, but it seems like a really long way to do it?

    The idea behind organizing your data in the manner implied by creating all these structures and/or arrays is called "virtualizing" your code. The idea that you're avoiding hard-coding everything. As an extreme example you don't create 20 button_events in code to handle 20 presets. You create one button_event that calls on an array of button channels. In the event you determine which of the buttons were pushed and from that determine which preset to send. It involves you lining up the data cells of the preset commands with the data cells of the buttons and what those buttons represent.

    A good rule of thumb is - if you find yourself placing an integer value (in your case the [1]), it implies you haven't virtualized your code far enough yet. (or there is always some case where it's an out lying thing and it's just easier (lazier) to just pop it in for that special case)

    Your code might look like this for example
    DEFINE_CONSTANT
    integer MyPreset_Buttons[]={
        1,2,3,4,5,6,7,8,9,10
        }
    DEFINE_EVENT
    
    button_event[TPs,MyPreset_Buttons]{
        push:{
            stack_var integer button_id;
            button_id=get_last(MyPreset_Buttons)
            send_String dvLights,"'FADEDIM,'itoa(Preset[button_id].Lt_Zone1.nIntensity),
                                    ','itoa(Preset[button_id].Lt_Zone1.nFadeTime),',','0[1:1]',$0D"
            } // push
        } // button_event
    

    (I broke up your long string build to two lines for ease of reading but it's still the same.

    Additionally, I'd be willing to bet you could pack away that
    '0[1:1]'
    at the end of the string in your presets data base as well so you're not hard coding that little section in the presets as well. Perhaps that section is not different from one preset to another or something. Anyway, hope that helps.
    e
  • JasonSJasonS If I had known it was going to be that kind of party... Posts: 227
    a_riot42 wrote: »
    Yes it is a struct array and is volatile, but that wasn't the difference, it was the nesting of structs. I think I will test it again since I haven't since the NX series came out. Perhaps they do memory management better, but I doubt it. Having struct within structs would be a nice feature for doing object-oriented type stuff (too bad we can't use pointers to functions as well)

    Pointers would be nice. It is clear from AMX's attitude toward Duet that they have ZERO interest in providing support for anything marginally complicated. They won't even let you speak directly with any of the Duet programmers.
  • ericmedleyericmedley Senior Member - 3709 Posts Posts: 4,141
    JasonS wrote: »

    Pointers would be nice. It is clear from AMX's attitude toward Duet that they have ZERO interest in providing support for anything marginally complicated. They won't even let you speak directly with any of the Duet programmers.

    Duet has been a white elephant for some time now. It's complicated. From zero support to zero documentation (in fact the only documentation to get started won't even compile) to utilizing an already out-of-date version of JAVA, etc... It was kind of a strange implementation of what could have conceivably been a pretty cool development environment.

    But, in fact, I don't think they ever intended it for us "forum types" ie: AMX Programmers. It's was really a way to get gear manufacturers to write modules for control. Most equipment manufactuers didnt want to send their expensive software engineers to learn this quirky Netlinx language. they already were spending big bucks hiring JAVA programmers. So, AMX glommed onto it via DUET, hoping the manufacturers would easily get their current programmers to also write modules.

    As we all know - the problem with that idea was that, while they might be good JAVA programmers with lots of industrial engineering chops, they had no idea how an AV control system worked or why we do the things we do.

    At every AMX Developers Conference I've been to we discussed the whole notion of going to some kind of more mainstream development environment. (Like JAVA, C#,MS Visual BASIC, etc...) It seems like an neat toy for us engineer types. But whenever they even approach the idea of making it so, it crashes on the rocks of having to migrate a whole bunch of people (a good chunk of us programmers) who are not 'classically' trained in modern objecct-oriented programming think and who are in many cases folks who sort just learned it on our own.

    I can say, having come up from the Computer Science/Engineering world, I've found the AV world sometimes a bit scary. We AV programmers sometimes don't follow more mainstream 'best practices'; particularly in the areas of code formatting, documentation and software version management. (Let alone just fricken backing up the source code) After all - we're just turning TVs on and off... It was a good gig, I got paid.

    So, while I would LOVE for us to migrate to something more mainstream (and I have no pony in that race - JAVA, C#, C++, cool by me) I really don't see our industry wanting to send all of us AV programmers to school to learn the new stuff - particularly when that same newly trained programmer would certainly now find much better paying jobs at many other manufactuers and whatnot.
  • fogled@mizzou[email protected] h4x354x0r Posts: 547
    This is pretty much off topic / just food for thought...

    LOL Yeah it's lazy AF from a programming standpoint, but when you're working in an archaic, numeric token based language, sometimes the damned number itself makes as much sense in the code, as anything else. When comparing code, I've found myself often far more willing to bend my programming to the language, than to bend the language to my programming. But that means my skill level is basically still 1980's procedural-based coding. Quite frankly bummed about the career dead-end corner I appear to painted myself into at this point.

    Also, for many years now, I've been thinking / imagining about an open-source platform for AV control, basically PHP/Python with some kind of SQL backend. I've even coded up the roughest framework for it, had it running on one project for awhile. But the combination of the "No custom development, must use vendor products as-is out of the box" mantra, along with realistic constraints on my time and not-very-good programming abilities, slowly killed it. It seems like EDU market could band together and develop something like this fairly easily.

    But, it's obviously not that easy, or cost effective, or perhaps it would be done already?
  • TUTechTUTech Junior Member Posts: 70
    Thanks again Eric. That is easy enough to do. The buttons are numbered differently so I have to put a little math in there.

    I was thinking there should be away to make " Preset[1].LT_Zone1.nIntensity" shorter. Pointers is what I was thinking about. I'll figure it out.

    Yes, I was also thinking "0,[1:1]" could be done differently. 0,[1:itoa(variable)] variable +1 There are 4 of them.
  • a_riot42a_riot42 AMX Wizard Posts: 1,619
    MLaletas wrote: »
    For me its pretty typical for my projects to have at least one nested structure. In my framework I have a room structure array in case I am doing a divisible/combinable room or multiple rooms off of one processor. Within that structure array I'll have another structure array nested for all sources for that room which will have all that data for that source (control method, inputs, outputs, name, etc....).

    You wouldn't see the slowness of nested structures if you are using them that way. If you use them to store lots of data that you constantly read and write to, you'll quickly notice that its much slower to access than arrays. My guess is for arrays, a lookup is just following a pointer, whereas for a nested structure, there are some calculations required to end up at the correct memory location. For XML/JSON and other formats that have a nested arrangement nested structs would be ideal, but I no longer do it that way unless the data is fairly small in size due to the speed issue. Hopefully its no longer the case with NX controllers.
    Paul
Sign In or Register to comment.