"dev42" wrote:Sure. Let's say in a sub A() you create a roScreen (or another huge chunk of data, say parsed multi-megabyte xml) and then you call from there sub B(), C() etc by passing that as argument. Each of them in turn may call sub-routines B1(), B2() etc as they see fit and may or may not pass the big structure to them. As long as none of them reaches out of its scope (local vars and fn args) to store roScreen in a global variable, you can be sure that when they return, ref-cnt will be back to 1 and on exit from A() the object will be disposed - you don't even have to explicitly set the variable to invalid.
I don't understand what "since leaving out of nested functions will be cleaning behind" means exactly. Can you expound on it a bit?
My other desire was to limit the passing of parameters unnecessarily *AND* to make the code easier to edit as a shorter parameter list seems more helpful to me.... but now that I've taken this to an extreme, passing "m" doesn't tell me much about what the function needs or will do.You got it - things should be done in moderation.
AS per freeing memory: do methods, functions attached to objects, free their local variables differently than global functions?No.
Warm on the 2nd, cold on the rest."EnTerr" wrote:
For edu-tainment's sake, i made here an artificial example to demonstrate how one "memory leak" happens: ...
- Is there something going on with the stack being initialized to 100 instead of 10?
and/or the pull() function only changing the ptr variable and not doing anything with the actual memory reserved in the array?
Arrays use contiguous memory, yet I thought I read that BrightScript does allow individual elements to be "released", am I getting warmer?
If we were to debug such a code fragment, what tools do we have to check the memory use?
... and boom, you forgot to do the cleaning at function's end. To do it right, you'd have to GOTO the end segment or cascade your code to the right by using extra IFs.
' *** setup globals here ***
' init obj's
for each obj in objList : obj.init()
' *** do Roku Event/Msg thing here ***
' process event
for each obj in objList : obj.doEvent(e)
' draw ea. obj
for each obj in objList : obj.draw()
for each obj in objList : obj.close()
' *** close globals here ***
You got it - things should be done in moderation.
Regarding passing "unnecessarily", let me give you this to mull about: using variable `X` passed as an argument is MUCH faster that using `m.X`. This is because in B/S dot-operators are dictionary lookups behind the scenes. Yes, every time - even in a loop. (I am not saying don't use m.X, just know "unqualified" X is faster)
Warm on the 2nd, cold on the rest.
Why RokuCo, WHY?!?
- if "home" is pressed, does gc get called? Yes, but ... not the same as if the app closed correctly? In light of the potential mess of refcnt's.
- what if... only *ONE* area assigns globals and everywhere else accesses them?
- a third point, because there have to be at least 3
To reiterate what you just said, "passed as an argument" ... specifically emphasizing "sending", right? So, what's better/preferable: ● B(m.loc) ● B(m.loc.x, m.loc.y) ● B(m)? ... when B() is called by A() and A() is most likely being called every time through the main loop!Well that depends on what exactly are you doing. I would say write whatever seems natural to you at first. Luckily in B/S whatever comes naturally - laziness, do less typing - is also faster. Working with a local variable ("x") is an order of magnitude (> 10x) faster than "dotting" as m.x (regardless whether for global or object member). SImplifying a little bit here: m.x is just syntax sugar for m["x"]. Using global functions and local variables is fast, anything that involves a dot - not so much. Don't get all crazy on me now and banish object use completely. Optimize later, you may not need it. (RokuMarkN frowns when i talk about performance, i know 8-) Sorry).
for i = 1 to lineLen
m.loc.x = m.loc.x + dx
m.loc.y = m.loc.y + dy
' loop-invariants moved out, much faster
x = m.loc.x : y = m.loc.y
for i = 1 to lineLen
x = x + dx
y = y + dy
So, you're just decrementing your own internal size counter, but never releasing any of the array's individual elements, right? You could, but not with your code, still access sYou got it!
, even when ptr < x.
function(): m.ptr = m.ptr - 1 : res = m.stk[m.ptr] : m.stk[m.ptr] = invalid : return res : end functionOr of course, i could have avoided re-inventing the wheel and just used roArray.push() and .pop() instead of rolling my own but that wouldn't have allowed me to demonstrate a "memory leak", now would it.
Your demo-code confuses me & is a construct I've not fully accepted ( it's not in my quiver ). How is s.push() or s.pull() even allowable if the stack function requires a parameter? ( Never-mind. It's the formatting. I'm doing the same thing in long format. Not only that, I don't [yet] use the ":" trick in my actual code. ) For clarity, the dim is only called once, right?Sorry - i don't usually write so dense but in the forum i go to great lengths to make code short so it can be easy to see at a glance - preferably without scroll bar at the code box.
(RokuMarkN frowns when i talk about performance, i know 8-) Sorry).
Indeed. Far FAR more important than performance is how the various choices affect the structure and maintainability of your code. Generally global variables are evil. There are some cases where globals are appropriate, but if you're not sure whether a variable should be global or not, it shouldn't.
Generally global variables are evil.
Why are global variables evil?
a = 100
a = func3()
m.a = 100