The Millionth Monkey Gets Its Typewriter.
Moderator: Moderators
Um... zwzsg, with all due respect... I don't think that's a better way to do things. I will do some proofs when I get home... which will, I hope, convince everybody that what I am doing here is significantly better than the approach you've posed there.
But, for those of you who can't wait for a proof... do a simple logic problem... which takes longer to go through a stack... 100 commands, or 10 commands? Because, short of making loops that execute every frame, that's what it comes down to...
But, for those of you who can't wait for a proof... do a simple logic problem... which takes longer to go through a stack... 100 commands, or 10 commands? Because, short of making loops that execute every frame, that's what it comes down to...
Can you explain more precisely what your radical improvment is?
First you asked other people to guess it, then you said you eliminated "turn now" (I don't understand that part, animation that are seen should never use now anyway), then you talk about synching and lockup (I don't understand that either, how multiplying the number of function running at once can be more synched than having a single function do all the walk animation), and when I look at the actual code I don't see where's the revolution. So please clear that up, and explain clearly what there is to see.
First you asked other people to guess it, then you said you eliminated "turn now" (I don't understand that part, animation that are seen should never use now anyway), then you talk about synching and lockup (I don't understand that either, how multiplying the number of function running at once can be more synched than having a single function do all the walk animation), and when I look at the actual code I don't see where's the revolution. So please clear that up, and explain clearly what there is to see.
It decreases the nubmer of items on the stack allowing mroe to be put on, aka faster code, allowing more of the units to appear onscreen for less lag.
Simply put. Yours may do the job but his is both easier to use understand and ammend/code while being a heck of a lot more efficient for the cob virtual machine to execute.
Once I'd read Arghs script it was nice and I could start thinking about changes and additions. What you posted was an intimidating mass of text I just didnt want to read it in full and go over it a second time like I did with Arghs.
We all have our preferences though
Simply put. Yours may do the job but his is both easier to use understand and ammend/code while being a heck of a lot more efficient for the cob virtual machine to execute.
Once I'd read Arghs script it was nice and I could start thinking about changes and additions. What you posted was an intimidating mass of text I just didnt want to read it in full and go over it a second time like I did with Arghs.
We all have our preferences though
KDR_11k wrote:What I see first and foremost is that his approach has less repeating code so if e.g. you wanted each leg to have an additional keyframe you'd add one line instead of however many you have there.
Maybe it was a bad idea to compare a unit with 8 legs totalling 32 degree of liberty with a unit with two legs totalling 4 degrees of liberty. And the macros I used made it easier to amend, but longer to read. Here's how I scripted a 2 legged unit:AF wrote:What you posted was an intimidating mass of text I just didnt want to read it in full and go over it a second time like I did with Arghs.
Code: Select all
#define SIG_BUILD 32
#define WALK_FASTER 300
#define WALK_SLOWER 100
StartMoving()
{
signal SIG_MOVE;
set-signal-mask SIG_MOVE;
while(1)
{
turn jambd to x-axis <8> speed <8>*WALK_FASTER/WALK_SLOWER;
turn tibd to x-axis <34> speed <34>*WALK_FASTER/WALK_SLOWER;
turn jambg to x-axis <0> speed <26>*WALK_FASTER/WALK_SLOWER;
turn tibg to x-axis <0> speed <34>*WALK_FASTER/WALK_SLOWER;
sleep 1000*WALK_SLOWER/WALK_FASTER;
turn jambd to x-axis <-52> speed <60>*WALK_FASTER/WALK_SLOWER;
turn tibd to x-axis <68> speed <34>*WALK_FASTER/WALK_SLOWER;
turn bassin to y-axis <20> speed <20>*WALK_FASTER/WALK_SLOWER;
turn jambd to y-axis <-20> speed <20>*WALK_FASTER/WALK_SLOWER;
turn jambg to y-axis <-20> speed <20>*WALK_FASTER/WALK_SLOWER;
sleep 1000*WALK_SLOWER/WALK_FASTER;
turn jambd to x-axis <0> speed <26>*WALK_FASTER/WALK_SLOWER;
turn tibd to x-axis <0> speed <34>*WALK_FASTER/WALK_SLOWER;
turn jambg to x-axis <8> speed <8>*WALK_FASTER/WALK_SLOWER;
turn tibg to x-axis <34> speed <34>*WALK_FASTER/WALK_SLOWER;
sleep 1000*WALK_SLOWER/WALK_FASTER;
turn jambg to x-axis <-52> speed <60>*WALK_FASTER/WALK_SLOWER;
turn tibg to x-axis <68> speed <34>*WALK_FASTER/WALK_SLOWER;
turn bassin to y-axis <-20> speed <20>*WALK_FASTER/WALK_SLOWER;
turn jambd to y-axis <20> speed <20>*WALK_FASTER/WALK_SLOWER;
turn jambg to y-axis <20> speed <20>*WALK_FASTER/WALK_SLOWER;
sleep 1000*WALK_SLOWER/WALK_FASTER;
}
}
StopMoving()
{
signal SIG_MOVE;
turn jambd to x-axis <0> speed <90>*WALK_FASTER/WALK_SLOWER;
turn tibd to x-axis <0> speed <90>*WALK_FASTER/WALK_SLOWER;
turn jambg to x-axis <0> speed <90>*WALK_FASTER/WALK_SLOWER;
turn tibg to x-axis <0> speed <90>*WALK_FASTER/WALK_SLOWER;
turn bassin to y-axis <0> speed <50>*WALK_FASTER/WALK_SLOWER;
turn jambd to y-axis <0> speed <50>*WALK_FASTER/WALK_SLOWER;
turn jambg to y-axis <0> speed <50>*WALK_FASTER/WALK_SLOWER;
}
I'm not sure what you call stack. But what I see is that with Arg's walkscript, you get eight function running at once just for the walk animation (MotionControl() , Go, MotionControl2() , Go2, MotionControl3() , Go3, MotionControl4() , Go4()), while for mine there is only one (StartMoving()). That means the cob machine has to run eight parrelel threads for each kbot. Well, if we assume that "call-script" is well optimised, the Go function would insert thmselves into each of the MotionControl, so you'll just have 4 threads. But that's still 4 threads to run in parallel for the COB virtual machine, it has to keep in the lines adresses of each, at each tick the COB virtual machine has to decrease 4 timers and check them, and so basically it's 4 times slower than having a single thread do the walk animation. Where's the efficiency gain, in multiplying the workload of the COB machine by 4? That can only bring more lag, what makes you say it could decrease lag? That I really don't get.AF wrote:It decreases the nubmer of items on the stack allowing mroe to be put on, aka faster code, allowing more of the units to appear onscreen for less lag. [...]being a heck of a lot more efficient for the cob virtual machine to execute.
In his method, each time he want one piece to be turned to a certain position, that's still one more line of codes, right? Has for the pause, he seem to have exactly as many as me but spread over more function, (so they are run in parallel instead of one after the other). And then he added all the complex mess of the MotionControl, which add lots of lines for nothing. Oh well, let's just count. My walkscript has four "phase" between four "pose", I'll assume his to since he roughly has the same number of turn. The two leg walkscript I posted has 44 lines. His code, when stripped of everything irrelevant to walkscript, is still 210 lines. For me 44<210. Btw here's what I kept to count his linesWhat I see first and foremost is that his approach has less repeating code so if e.g. you wanted each leg to have an additional keyframe you'd add one line instead of however many you have there.
static-var bMoving;
#define SIG_MOVE 1
Go()
{
// normal steps
if (bMoving)
{
// RightFront fronts
wait-for-turn rfbodyshaft around x-axis;
turn rfbodyshaft to x-axis <-50> speed <325>;
wait-for-turn rfbodyshaft around x-axis;
move rfpistonarm to y-axis [-0.3] speed [15];
turn rfbodyshaft to x-axis <0> speed <325>;
}
if (bMoving)
{
// RightFront backs
wait-for-turn rfbodyshaft around x-axis;
turn rfbodyshaft to x-axis <50> speed <325>;
move rfpistonarm to y-axis [0.4] speed [10];
wait-for-turn rfbodyshaft around x-axis;
turn rfbodyshaft to x-axis <0> speed <325>;
}
return 0;
}
Go2()
{
// normal steps
if (bMoving)
{
// RightBack backs
wait-for-turn rrbodyshaft around x-axis;
turn rrbodyshaft to x-axis <50> speed <325>;
move rrpistonarm to y-axis [0.4] speed [10];
wait-for-turn rrbodyshaft around x-axis;
turn rrbodyshaft to x-axis <0> speed <325>;
}
if (bMoving)
{
// RightBack fronts
wait-for-turn rrbodyshaft around x-axis;
turn rrbodyshaft to x-axis <-50> speed <325>;
wait-for-turn rrbodyshaft around x-axis;
move rrpistonarm to y-axis [-0.3] speed [15];
turn rrbodyshaft to x-axis <0> speed <325>;
}
return 0;
}
Go3()
{
// normal steps
if (bMoving)
{
// LeftBack fronts
wait-for-turn lrbodyshaft around x-axis;
turn lrbodyshaft to x-axis <-50> speed <325>;
wait-for-turn lrbodyshaft around x-axis;
move lrpistonarm to y-axis [-0.3] speed [15];
turn lrbodyshaft to x-axis <0> speed <325>;
}
if (bMoving)
{
// LeftBack backs
wait-for-turn lrbodyshaft around x-axis;
turn lrbodyshaft to x-axis <50> speed <325>;
move lrpistonarm to y-axis [0.4] speed [10];
wait-for-turn lrbodyshaft around x-axis;
turn lrbodyshaft to x-axis <0> speed <325>;
}
return 0;
}
Go4()
{
// normal steps
if (bMoving)
{
// LeftFront backs
wait-for-turn lfbodyshaft around x-axis;
turn lfbodyshaft to x-axis <50> speed <325>;
move lfpistonarm to y-axis [0.4] speed [10];
wait-for-turn lfbodyshaft around x-axis;
turn lfbodyshaft to x-axis <0> speed <325>;
}
if (bMoving)
{
// LeftFront fronts
wait-for-turn lfbodyshaft around x-axis;
turn lfbodyshaft to x-axis <-50> speed <325>;
wait-for-turn lfbodyshaft around x-axis;
move lfpistonarm to y-axis [-0.3] speed [15];
turn lfbodyshaft to x-axis <0> speed <325>;
}
return 0;
}
Stop()
// stop motion
{
sleep 200;
// RF and LR legs to start
turn rfbodyshaft to x-axis <0> now;
move rfpistonarm to y-axis [0] now;
turn lrbodyshaft to x-axis <10.2> now;
move lfpistonarm to y-axis [0] now;
sleep 100;
// RR and LF legs to start
turn rrbodyshaft to x-axis <10.2> now;
move rrpistonarm to y-axis [0] now;
turn lfbodyshaft to x-axis <0> now;
move lfpistonarm to y-axis [0] now;
sleep 100;
return 0;
}
MotionControl()
{ var moving,just_moved;
just_moved = 1;
WHILE ( TRUE )
{ moving = bMoving ;
IF (moving)
{
just_moved = 1;
call-script Go(bMoving);
}
IF (!moving)
{ IF (just_moved)
{ just_moved = 0;
call-script Stop();
}
SLEEP 50;
}
}
}
MotionControl2()
{ var moving,just_moved;
just_moved = 1;
WHILE ( TRUE )
{ moving = bMoving ;
IF (moving)
{
just_moved = 1;
call-script Go2();
}
IF (!moving)
{ IF (just_moved)
{
just_moved = 0;
}
SLEEP 100;
}
}
}
MotionControl3()
{ var moving,just_moved;
just_moved = 1;
WHILE ( TRUE )
{ moving = bMoving ;
IF (moving)
{
just_moved = 1;
call-script Go3();
}
IF (!moving)
{ IF (just_moved)
{
just_moved = 0;
}
SLEEP 100;
}
}
}
MotionControl4()
{ var moving,just_moved;
just_moved = 1;
WHILE ( TRUE )
{ moving = bMoving ;
IF (moving)
{
just_moved = 1;
call-script Go4();
}
IF (!moving)
{ IF (just_moved)
{
just_moved = 0;
}
SLEEP 100;
}
}
}
start-script MotionControl();// In Create() but I don't count the "Create()" line as it has to be there anyway
start-script MotionControl2();
start-script MotionControl3();
start-script MotionControl4();
bMoving = 0;// In Create() but I don't count the "}" line as it has to be there anyway
StartMoving()
{
bMoving = 1;
return 0;
}
StopMoving()
{
bMoving = 0;
return 0;
}
I don't understand this. Please explain! What do you call stack? In which way you code has less commands being executed? Why is the only alternative something that execute every frame? Which loop?Argh wrote:which takes longer to go through a stack... 100 commands, or 10 commands? Because, short of making loops that execute every frame, that's what it comes down to...
I still don't see the radical improvment in Argh's script. I eventually gathered he used one function for each limb, instead of one function for every limb, but that only make his code less efficient and more laggy! I fail to see where's the brillant idea. Please open my eyes!
Ok... first off, I'm developing some further, concrete proofs. This will take a bit, because of IRL circumstances, so please understand that I'm not being rude by refusing to answer your questions in full at this point.
But, here are a few answers:
1. Your code has to execute many, many more mathematical operations per cycle than mine does. Each one of your lines:
A. Run through the BOS's many, many lines every frame, because you don't have MotionControl limiting how many times a second you're checking the state of Moving.
B. Move to the Function being called.
C. Move to the appropriate line in the Function.
D. Execute a mathematical operation on the line.
E. Put that into memory, and pass that to the part of Spring that actually moves and draws parts of models.
2. Yes, my code looks longer than your two-leg example script. However, most of it is not being called on any given frame. In fact, most of it is either in the process of Wait-For-Turn, or is sleeping. The only real bugbear, which is unfortunately unavoidable, is the series of logical checks in MotionControl, which must be executed every tenth of a second or so (which is not too burdensome).
Your script, however, is executing commands every frame, because of the math checks and other things. This is not ideal... and it's why, along with other problems, I have been searching for a real alternative, because, as your Scorpion clearly points out, there is a point where it's inefficient. I don't suppose anybody tried building 20 of them and then watching CPU load? It's quite instructive! I will be tackling that beast and optimizing it also... but not yet, unfortunately IRL issues are in the way today and tomorrow, so please be patient, I will hit all of this in greater detail Friday.
3. You're using NOW, which has fundamental limitations in Spring, which I will get into more detail about later.
4. Here's a two-leg walk-cycle with three axis of motion. Please bear in mind that this is just an example, as I don't have a two-legged walking thing in NanoBlobs (yet).
5. Consider the implications of the following:
Spring doesn't care how many scripts are running simultaneously within a given COB- they're all just points on the same thread. What is the limiting factor... is how many simultaneous things are being asked to execute each second by the COB interpreter, not how many Functions are running simultaneously.
But, here are a few answers:
1. Your code has to execute many, many more mathematical operations per cycle than mine does. Each one of your lines:
Has a Turn, which is conditional on the results of (z-axis 0 - (LEG__1_DOWN_ANGLE)). This is a major disadvantage from a speed standpoint. Spring has to do several things here:turn leg111 to z-axis 0 - (LEG__1_DOWN_ANGLE) now;
A. Run through the BOS's many, many lines every frame, because you don't have MotionControl limiting how many times a second you're checking the state of Moving.
B. Move to the Function being called.
C. Move to the appropriate line in the Function.
D. Execute a mathematical operation on the line.
E. Put that into memory, and pass that to the part of Spring that actually moves and draws parts of models.
2. Yes, my code looks longer than your two-leg example script. However, most of it is not being called on any given frame. In fact, most of it is either in the process of Wait-For-Turn, or is sleeping. The only real bugbear, which is unfortunately unavoidable, is the series of logical checks in MotionControl, which must be executed every tenth of a second or so (which is not too burdensome).
Your script, however, is executing commands every frame, because of the math checks and other things. This is not ideal... and it's why, along with other problems, I have been searching for a real alternative, because, as your Scorpion clearly points out, there is a point where it's inefficient. I don't suppose anybody tried building 20 of them and then watching CPU load? It's quite instructive! I will be tackling that beast and optimizing it also... but not yet, unfortunately IRL issues are in the way today and tomorrow, so please be patient, I will hit all of this in greater detail Friday.
3. You're using NOW, which has fundamental limitations in Spring, which I will get into more detail about later.
4. Here's a two-leg walk-cycle with three axis of motion. Please bear in mind that this is just an example, as I don't have a two-legged walking thing in NanoBlobs (yet).
Code: Select all
Go()
{
// normal steps
if (bMoving)
{
// RightSide fronts
wait-for-turn R_THIGH around x-axis;
turn R_THIGH to x-axis <-50> speed <325>;
turn R_KNEE to x-axis <40> speed <325>;
turn R_FOOT to x-axis <15> speed <150>;
wait-for-turn R_THIGH around x-axis;
turn R_THIGH to x-axis <0> speed <325>;
}
if (bMoving)
{
// RightSide backs
wait-for-turn R_THIGH around x-axis;
turn R_THIGH to x-axis <50> speed <325>;
turn R_KNEE to x-axis <0> speed <325>;
turn R_FOOT to x-axis <-50> speed <325>;
wait-for-turn R_THIGH around x-axis;
turn R_THIGH to x-axis <0> speed <325>;
}
}
Go2()
{
// normal steps
if (bMoving)
{
// LeftSide backs
wait-for-turn L_THIGH around x-axis;
turn L_THIGH to x-axis <50> speed <325>;
turn L_KNEE to x-axis <0> speed <325>;
turn L_FOOT to x-axis <-50> speed <325>;
wait-for-turn L_THIGH around x-axis;
turn L_THIGH to x-axis <0> speed <325>;
}
if (bMoving)
{
// LeftSide fronts
wait-for-turn L_THIGH around x-axis;
turn L_THIGH to x-axis <-50> speed <325>;
turn L_KNEE to x-axis <40> speed <325>;
turn L_FOOT to x-axis <15> speed <150>;
wait-for-turn L_THIGH around x-axis;
turn L_THIGH to x-axis <0> speed <325>;
}
}
Stop()
// stop motion
{
sleep 100;
// Legs to start
turn R_THIGH to x-axis <0> now;
turn L_THIGH to x-axis <0> now;
turn R_KNEE to x-axis <0> now;
turn L_KNEE to x-axis <0> now;
turn R_FOOT to x-axis <0> now;
turn L_FOOT to x-axis <0> now;
sleep 100;
}
MotionControl()
{ var moving,just_moved;
just_moved = 1;
WHILE ( TRUE )
{ moving = bMoving ;
IF (moving)
{
just_moved = 1;
call-script Go(bMoving);
}
IF (!moving)
{ IF (just_moved)
{ just_moved = 0;
call-script Stop();
}
SLEEP 50;
}
}
}
MotionControl2()
{ var moving,just_moved;
just_moved = 1;
WHILE ( TRUE )
{ moving = bMoving ;
IF (moving)
{
just_moved = 1;
call-script Go2();
}
IF (!moving)
{ IF (just_moved)
{
just_moved = 0;
}
SLEEP 100;
}
}
}
Spring doesn't care how many scripts are running simultaneously within a given COB- they're all just points on the same thread. What is the limiting factor... is how many simultaneous things are being asked to execute each second by the COB interpreter, not how many Functions are running simultaneously.
zwzsg part of what Arghs saying is because of the internal implementation of the COB Virtual machine.
If I recall correctly, it's a stack based system, thus it executes instructions off of the stack.
(for those reading who dont knwo what a stack is, thinking of it as a queue where you put things on the stack/que, then execute/throw away stuff at the other end)
Here you are sayign that Arghs code is worse because ti has more lines.
1 line != 1 instruction
c = a+b != 1 instruction
at the very least
1 :find memory for c
2 :allocate a new value to that memory
3 :get the value of a
4 :get the value of b
5 :find memory for temporary variable d
6 :allocate temporary value d
7 :perform a+b
8 :store the result in temporary value d
9 :assign value c the contents of value d
10 :delete value in d
11 :deallocate memory used for d
12 :destroy all references to temporary value in VM(dependent on implementation(garbage collector))
somewhere around 11 or 12 instructions for a single line.
How large is your bos script when compiled? How does it compair to Arghs bos script? For one if it's larger then it definately has more instructions as thats the whole point of compiling, to translate into cob vm instructions as bytecode.
Ontop of that how many instructions per second are executed?
Argh has a big point with his sleeps and waits.
In ym own experience a certain piece fo java code that shall not be named had a neverending loop running it while(){}, it had no waits or sleeps or delays of any kind. It would check if a connection was open and exit if it wasnt, otherwise run a single large function.
I found it became very laggy at times and as a result was capable of crippling itself and thus wasnt very good for anything but lightweight oeprations as it was originally used for. However I with a few others found that assigning a timer to call the update function at time slots rather than continuosly in a neverendign loop reduced cpu usage by several orders of magnitude from 100% cpu usage to barely measurable amounts.
n# lines dosnt matter. It's number of operations/instructions and calculations that determine speed. Albeit more lines means more chances to add extra instructions.
If I recall correctly, it's a stack based system, thus it executes instructions off of the stack.
(for those reading who dont knwo what a stack is, thinking of it as a queue where you put things on the stack/que, then execute/throw away stuff at the other end)
Here you are sayign that Arghs code is worse because ti has more lines.
1 line != 1 instruction
c = a+b != 1 instruction
at the very least
1 :find memory for c
2 :allocate a new value to that memory
3 :get the value of a
4 :get the value of b
5 :find memory for temporary variable d
6 :allocate temporary value d
7 :perform a+b
8 :store the result in temporary value d
9 :assign value c the contents of value d
10 :delete value in d
11 :deallocate memory used for d
12 :destroy all references to temporary value in VM(dependent on implementation(garbage collector))
somewhere around 11 or 12 instructions for a single line.
How large is your bos script when compiled? How does it compair to Arghs bos script? For one if it's larger then it definately has more instructions as thats the whole point of compiling, to translate into cob vm instructions as bytecode.
Ontop of that how many instructions per second are executed?
Argh has a big point with his sleeps and waits.
In ym own experience a certain piece fo java code that shall not be named had a neverending loop running it while(){}, it had no waits or sleeps or delays of any kind. It would check if a connection was open and exit if it wasnt, otherwise run a single large function.
I found it became very laggy at times and as a result was capable of crippling itself and thus wasnt very good for anything but lightweight oeprations as it was originally used for. However I with a few others found that assigning a timer to call the update function at time slots rather than continuosly in a neverendign loop reduced cpu usage by several orders of magnitude from 100% cpu usage to barely measurable amounts.
n# lines dosnt matter. It's number of operations/instructions and calculations that determine speed. Albeit more lines means more chances to add extra instructions.
What do you call "cycle"?, Is the cycle of Spring main loop, that's executed between every image, or cycle of the whatever script function? If it's the cycle of Spring main loop, then yours does 4x times as many mathematical operation as mine.1. Your code has to execute many, many more mathematical operations per cycle than mine does. Each one of your lines:
Erm, where do you see a condition? 0 - (LEG__1_DOWN_ANGLE) is not a condition, it's the angle the piece is turning toward to. Unless you're using the "spin" command, and you're not, there is no way to avoid passing the desired angle in every turn command.turn leg111 to z-axis 0 - (LEG__1_DOWN_ANGLE) now;
Has a Turn, which is conditional on the results of (z-axis 0 - (LEG__1_DOWN_ANGLE)). This is a major disadvantage from a speed standpoint. Spring has to do several things here:
What? On most frames, I run only one line, the "sleep", or the "wait-for", and for a few frames, I run max 4 turn, then a "sleep" or "wait-for". As for the state of bMoving, I don't even check it anywhere in the 2 legs walkscript I posted.A. Run through the BOS's many, many lines every frame, because you don't have MotionControl limiting how many times a second you're checking the state of Moving.
In the Scorpion walkscript, I'm using "now" only once in the lifetime of every scorpion, in the create, so it's not spawn with legs all horizontal like in the 3do. But there's no "now" in the walkscript".3. You're using NOW, which has fundamental limitations in Spring, which I will get into more detail about later.
In the 2 leg walkscript I just posted, there isn't any "now"!. Don't tell me I use "now" which is inefficient, as I'm not using "now".
Hmm, on any give frame, my code run even lines fewer than yours. The MotionControl is avoidable. Unlike what you said, your MotionControl isn't executed every tenth of a second or so, as most of time it's busy waiting for the "go" function to return, but if it were, then it would be really burdensome.2. Yes, my code looks longer than your two-leg example script. However, most of it is not being called on any given frame. In fact, most of it is either in the process of Wait-For-Turn, or is sleeping. The only real bugbear, which is unfortunately unavoidable, is the series of logical checks in MotionControl, which must be executed every tenth of a second or so (which is not too burdensome).
My script execute the minimal number of commands every frame. Most of frames it sleeps, and when it's done sleeping it turn only what must be turned and sleep again. You sound like you believe the COB machine goes throught the whole walk script every time! Well, it does not, "sleep" and "wait-for" are here for a reason.Your script, however, is executing commands every frame, because of the math checks and other things. This is not ideal...
I don't believe that. I'm pretty sure Spring do care how many scripts are running simultaneously within a given COB. As for many things are done each second by the COB interpreter, I already do the minimum. The only way to have less would be to combine the walkscript function with any other function being run continuously, like the SmokeUnit, but then it wouldn't be easy to stop walking and continue smoking (for instance).5. Consider the implications of the following:
Spring doesn't care how many scripts are running simultaneously within a given COB- they're all just points on the same thread. What is the limiting factor... is how many simultaneous things are being asked to execute each second by the COB interpreter, not how many Functions are running simultaneously.
I agree with that. I was just counting the lines because someone said Arg script had less lines, so was easier to read and modify. But Arg's script has both more lines and more instruction effectively being run each frame, so.. And don't worry, I know since long ago that everlooping while without sleep or wait-for are great ways to hang a computer.AF wrote:n# lines dosnt matter. It's number of operations/instructions and calculations that determine speed. Albeit more lines means more chances to add extra instructions.
I'll mount your script, and mine, on the very same T.M.U. kbot, and upload them and stress them, so you won't have that excuse.Argh wrote:Ok... first off, I'm developing some further, concrete proofs. This will take a bit, because of IRL circumstances, so please understand that I'm not being rude by refusing to answer your questions in full at this point.
[...]
I don't suppose anybody tried building 20 of them and then watching CPU load? It's quite instructive! I will be tackling that beast and optimizing it also... but not yet, unfortunately IRL issues are in the way today and tomorrow, so please be patient, I will hit all of this in greater detail Friday.
Ok. So I took the ArmAmazon, an unreleased kbot by Legion from T.M.U.
Made two version:
AmazonA, with Arg walkscript
AmazonZ, with exactly the same motion, (same turn, same angle, same speed), but scripted my way.
I stripped the scripts for everything besides walkscript (no smoking, no aiming, no killed, very bare scripts).
The experimental protocol was the following:
- Quit any Spring running, and run a fresh new instance of Spring
- Played on the map "The Cold Place", which has lots of free place
- .cheat, then pause then
- Spawned 1000 Amazons.
- Gave them a move order
- Moved the camera to the other side of the map, zoomed max to the ground
- Unpaused
- Pressed B and watched the values
Did it both for AmazonA and AmazonZ, and, while the difference is thin, it is still there:
- AmazonA (Arg WalkScript)
- AmazonZ (zwzsg walkscript)
Arg script use 15%, mine 6.5%. Ok, I don't really know percent of what.
So with Arg script, FPS is 4 frame per second, with mine, it's 11 frame per seconds (yes I have an old bad computer).
And that's with the second version of Arg script, with only two threads running at once instead of four. (While I use only one).
This was the comparaison between walkscript when the unit is actually walking, if we were to also give a look at what happens when the units are not walking: Arg script still has two threads busy looping when the 1000 kbots are standing still, which show as a 13% next to script in "B" mode, while on my script, there are 0 thread running when the 1000 kbots are standing still, which show as a 0.0% next to script in "B" mode.
I uploaded AmazonA and AmazonZ here:
Amazon_WalkScript_StressTest.ufo
In case anyone wants to examine the script to check I didn't corrupt Arg script, to check that both do exactly the same animation, and to repeat the experiment.
I am still wondering what's the improvment in Argh script, as I cannot find any aspect in which his way his better::
- Argh's way make longer BOS than mine
- Argh's way make longer COB than mine
- Argh's way use one static var and two local var, mine none of each.
- Argh's way has two function continuously looping, mine only one, and only when walking. (Heavier to run ingame)
- Argh's way has 6 functions (not counting create) in the bos, mine 2. (More difficult to read)
- Argh's way keep the messy and confusing Cavedog's way, with MotionControl, mine is clean and fresh and to the point.
- Argh's way eat twice more CPU than mine when walking
- Argh's way eat +oo more CPU than mine when standing still
etc...
Made two version:
AmazonA, with Arg walkscript
AmazonZ, with exactly the same motion, (same turn, same angle, same speed), but scripted my way.
I stripped the scripts for everything besides walkscript (no smoking, no aiming, no killed, very bare scripts).
The experimental protocol was the following:
- Quit any Spring running, and run a fresh new instance of Spring
- Played on the map "The Cold Place", which has lots of free place
- .cheat, then pause then
- Spawned 1000 Amazons.
- Gave them a move order
- Moved the camera to the other side of the map, zoomed max to the ground
- Unpaused
- Pressed B and watched the values
Did it both for AmazonA and AmazonZ, and, while the difference is thin, it is still there:
- AmazonA (Arg WalkScript)
- AmazonZ (zwzsg walkscript)
Arg script use 15%, mine 6.5%. Ok, I don't really know percent of what.
So with Arg script, FPS is 4 frame per second, with mine, it's 11 frame per seconds (yes I have an old bad computer).
And that's with the second version of Arg script, with only two threads running at once instead of four. (While I use only one).
This was the comparaison between walkscript when the unit is actually walking, if we were to also give a look at what happens when the units are not walking: Arg script still has two threads busy looping when the 1000 kbots are standing still, which show as a 13% next to script in "B" mode, while on my script, there are 0 thread running when the 1000 kbots are standing still, which show as a 0.0% next to script in "B" mode.
I uploaded AmazonA and AmazonZ here:
Amazon_WalkScript_StressTest.ufo
In case anyone wants to examine the script to check I didn't corrupt Arg script, to check that both do exactly the same animation, and to repeat the experiment.
I am still wondering what's the improvment in Argh script, as I cannot find any aspect in which his way his better::
- Argh's way make longer BOS than mine
- Argh's way make longer COB than mine
- Argh's way use one static var and two local var, mine none of each.
- Argh's way has two function continuously looping, mine only one, and only when walking. (Heavier to run ingame)
- Argh's way has 6 functions (not counting create) in the bos, mine 2. (More difficult to read)
- Argh's way keep the messy and confusing Cavedog's way, with MotionControl, mine is clean and fresh and to the point.
- Argh's way eat twice more CPU than mine when walking
- Argh's way eat +oo more CPU than mine when standing still
etc...
Last edited by zwzsg on 16 Aug 2006, 22:54, edited 1 time in total.
Arghs shot looks like the square has had mroe tiem to disperse which might lead to mroe changes anyways as they start bumping into eachother, which would cause a large spike in UnitHandler and slow update anyways. I expect the same would happen for zwzsg script too a second or two later regardless of what script zwzsg used.
This test should be reran with the units spaced out before told to move.
This test should be reran with the units spaced out before told to move.
Please do, as an experiment result can only be truely accepted once it has been repetead by other people:AF wrote:This test should be reran with the units spaced out before told to move.
Here's the units : Amazon_WalkScript_StressTest.ufo
- Lindir The Green
- Posts: 815
- Joined: 04 May 2005, 15:09
Well, I did my own experiment with my 2.8 Ghz Pentium 4 and 1 Gig of RAM.
The map was greener_fields, and I did the same test as zwzsg. For the idle test, I just tested for 30 seconds, and for the moving test, I waited until the units were pretty much staying in the same position relative to each other, and had moved about a third of the way across. Results:
AmazonZ====
Idle: 85 FPS
Moving: 31 FPS
AmazonA====
Idle: 85 FPS
Moving: 31 FPS
Hey, look at that. They are exactly the same. There may be a difference, but it is negligable with a mid-high end machine.
The map was greener_fields, and I did the same test as zwzsg. For the idle test, I just tested for 30 seconds, and for the moving test, I waited until the units were pretty much staying in the same position relative to each other, and had moved about a third of the way across. Results:
AmazonZ====
Idle: 85 FPS
Moving: 31 FPS
AmazonA====
Idle: 85 FPS
Moving: 31 FPS
Hey, look at that. They are exactly the same. There may be a difference, but it is negligable with a mid-high end machine.
- LathanStanley
- Posts: 1429
- Joined: 20 Jun 2005, 05:16
why does everyone in this community get a harddon for shooting others down???
Argh said he is STILL working on it.. meaning, it isn't finished yet, you are comparing a cake half-baked to a finished one...
let him finish it, then compare it... in ALL types of situations... just because yours works better on a bipedal robot dosen't mean that args may not work better on something with 200 legs...
thats the whole point of the way his code is scripted, it SHORTENS the calculations for a VERY heavy legged object >4 legs... vs. your calculation gets huge for a creature with >4 legs....
Argh's script will have its place, as so will yours.. just quit telling him he's "wrong" etc.
Argh said he is STILL working on it.. meaning, it isn't finished yet, you are comparing a cake half-baked to a finished one...
let him finish it, then compare it... in ALL types of situations... just because yours works better on a bipedal robot dosen't mean that args may not work better on something with 200 legs...

thats the whole point of the way his code is scripted, it SHORTENS the calculations for a VERY heavy legged object >4 legs... vs. your calculation gets huge for a creature with >4 legs....
Argh's script will have its place, as so will yours.. just quit telling him he's "wrong" etc.
I still cannot understand what makes you say that, that's why I'm looking and comparing and investigating and asking.LathanStanley wrote:thats the whole point of the way his code is scripted, it SHORTENS the calculations for a VERY heavy legged object >4 legs... vs. your calculation gets huge for a creature with >4 legs....
- LathanStanley
- Posts: 1429
- Joined: 20 Jun 2005, 05:16