Trying to simplify a gosub routine

wapo54001

Senior Member
There are two conditions which call the same subroutine. Each condition consists of two elements. Is there any way to reduce the code by combining the two tests into a single line like this:

"if x AND y OR a AND b THEN GOSUB"

This is the code that seems to work:

Code:
if w6=1 AND w1 < 110 then
   gosub lighton 
elseif w6=2 AND w1 < 164 then
   gosub lighton
else
   gosub lightoff
endif
And this is the code that doesn't seem to work but I'd like to make work:
Code:
if w6=1 AND w1 < 110 OR w6=2 AND w1<164 then
Any thoughts welcome!
 

inglewoodpete

Senior Member
I haven't checked to see if the code works, but it does compile without any syntax errors. Check that you have the Enhanced Compiler Option selected (View_Menu/Options/Editor_Tab).

Remember that the interpreter executes operators in sequential order, so there may be a problem with the sequence of your logic. Can you tell us what the exact symptoms of the problem are?
 

marcos.placona

Senior Member
I was about to say that I wasn't sure that AND and OR gates could be used on the same sentence. Although it wouldn't make much sense to not have this possibility, as inglewoodpete just stated, it might be handy if you could tell us what errors you're getting.
 

wapo54001

Senior Member
The code supports an 08M that reads pressure sensors and outputs the 'translated' results to a panel meter. I have set it up so that I can translate from two different sensors (15psi & 100psi full scale) by setting a jumper.

I have a warning light that flashes when pressure drops below a certain point, and that point is different for the two pressure ranges, though the voltage output of the sensors is the same (.5~4.5v).

In order for the light to work properly, the program must be able to tell which pressure sensor is in use and then test for the switch point associated with that particular sensor.

The symptom is that the light does not come on when it should when I try to use the single line to test for both sensor/pressure combinations. And yes, it does pass the Syntax test. I was hoping that someone could tell me what is wrong with my syntax or tell me that it can't be done that way.
 

hippy

Ex-Staff (retired)
There has been some discussion on mixed AND-OR expression earlier.

I haven't searched but from memory it seemed the conditionals were evaluated right to left in a real PICAXE ( and there is a logical reasoning to doing that if it is the case ). This is different behaviour to how the simulator evaluates things.

Technical's recommendation is not to mix AND with OR, and I think I'd go along with that.

In this particular case, because conditionals have no precedence ( they are evaluated strictly in sequence, left to right or vice-versa, as noted by inglewoodpete ) there is no way to combine the IF-ELSEIF into a single conditional expression.

What you have in the IF-ELSEIF is the best way to do it. If you need to save a GOSUB or code space there are ways to achieve that, so if it is the case we can follow that optimisation up.
 

marcos.placona

Senior Member
It'd be best used if you could do something like:

if (w6=1 AND w1 < 110) OR (w6=2 AND w1<164) then
By using the parenthesis, you can identify what happens first. I haven't tested it myself, but think it's a way to go for that.
 

wapo54001

Senior Member
Alas, parentheses don't work here. I don't think they work anywhere in Picaxe code -- they sure don't work when doing math.
 

wapo54001

Senior Member
I am trying to stay with the 08M and keeping code tight. In this particular instance I have space to spare but in other instances I'm at the "critical" point. Is there anywhere one can go to learn how to really compact code? I know there has been discussion that readability suffers when you streamline, but on another project I am at the point where I need to leave a feature out, or otherwise somehow find about 15 bytes.
 

Dippy

Moderator
Mixing things, when there aren't any parentheses, can get you in a right pickle.

I'm not sure how much code space you'd save, but I prefer the layout of your first version. It's clear. To me that is worth a couple of bytes.
And you may come to agree when you look at it again in 2 months time.

If space is really tight then there may be other ways to save space.
 

hippy

Ex-Staff (retired)
@ marcos : Yes, if PICAXE allowed that it would be great, but it doesn't :)

@ wapo54001 : Learning to create really compact code is more an exercise in doing and experiencing it. It's a bit like learning to bake a perfect meal, there are some rules but trying to define them all and exactly is hard.

If you want really compact code you have to forego all those things which make coding easier, IF-THEN-ELSE, IF-ELSEIF, SELECT CASE, DO-LOOP ( although FOR-NEXT is usually better than any other options ), and you have to start to get into Spaghetti Coding by design, letting routines fall through into others rather than have RETURN and all sorts of other nastiness.
 
Last edited:

wapo54001

Senior Member
Hippy, that is *not* an appealing alternative for me. I'm a hardware guy, and I need all the help I can get with the software. If it doesn't make sense when I read it, I sure don't want to put it in my chip!
 

hippy

Ex-Staff (retired)
That is the big challenge of programming; readable, understandable code and highly optimised code are at opposite sides of the spectrum. Even with a good optimising compiler one can only get part way there.

If documenting while only having a single sheet of paper, you either suffer using shorthand, or give up on the single sheet and go and buy a notepad.

Unfortunately it's one or the other. In this case it equates to moving up a level to an 18X with enough capacity to hold the code how you want it written, and that may be undesirable for a whole lot of reasons.

Turn the issue on its head and it becomes one of using the right tools ( processor or coding style ) for the job, stick with a particular tool and you can only do certain jobs.
 

moxhamj

New Member
I'm going with Dippy et al - I like your working code - if then else etc. Re space, try reading other people's code. Eg Hippy has some cunning tricks with the LCD display. One that has helped me a lot is using pulsout on a pin instead of high x, low x. Also using bitwise AND and OR tests on pins and understanding binary. And writing a complicated program with lots of gosubs and then realising that a gosub is only called once - so that bit of code can be pasted back into where the gosub was. And using lookup tables in eeprom rather than testing things in code.

Re running out of space, I think I read somewhere that hippy's favourite picaxe was the 18X (pls correct me if this is wrong). I started by trying to fit code into the smaller picaxes, but I'm now coming to like the 18X a lot more. I even tend to surround it with a few support picaxes like 08s and 08Ms. Very simple programs like flashing a led are fine, but once a program gets complex it is really helpful to know where it is up to, which means an LCD and that really means an 18X.

Also I like to keep all the picaxes in the parts drawer. If I run out of space, just grab the next one up in the series and port the code across. When I work out my hourly rate and the cost difference between picaxes and the time it takes to fully optimise code, it is cheaper to pay a few dollars more for a bigger picaxe. But that is just my experience. I do appreciate there is a great feeling in shoehorning a complex program into a little chip.
 
Last edited:

hippy

Ex-Staff (retired)
Yes, I still say the 18X is my favourite although I might be swayed towards the 40X1 if I were doing more PICAXE work these days given it's not much more expensive. I doubt it has as much scope for hacking especially now most things are built into the firmare - You may have noticed I enjoy the hobby of hacking far more than working on real projects. Beating the impossible is what I like, and when it's handed on a plate where's the challenge in that :)

For real projects, from a software and hardware point of view, the more there is the better. A project can always be reduced in scale later but it's harder to make it bigger.

There is enjoyment in doing a project with an intent to get minimum code size ( like those LCD routines ) but when program memory starts to get tight unexpectedly one ends up spending more time trying to shrink what's there than adding what one wants to do and it gets frustrating and stops being fun. I hate losing momentum in a project.
 

hippy

Ex-Staff (retired)
Going back to the original code ...

Code:
if w6=1 AND w1 < 110 then
   gosub lighton 
elseif w6=2 AND w1 < 164 then
   gosub lighton
else
   gosub lightoff
endif
If I were doing this and code space and gosub count were no object I'd have quite probably chosen this as the cleareset visualisation of what was going on ...

Code:
Select Case w6
  Case 1    : If w1 < 110 Then
                Gosub LightOn
              Else
                Gosub LightOff
              End If
  Case 2    : If w1 < 164 Then
                Gosub LightOn
              Else
                Gosub LightOff
              End If
  Case Else : Gosub LightOff
End Select
 

westaust55

Moderator
Wapo stated:
Alas, parentheses don't work here. I don't think they work anywhere in Picaxe code -- they sure don't work when doing math.
From PICAXE programming manual section 2 page 20:
On X1 and X2 parts it is possible to enclose part equations in brackets e.g.
let w1 = w2 / (b5 + 2)
But when I tried this in passing previously myself the Programming Editor (set to the 28X1) gave an error message until the brackets were removed.
 

BCJKiwi

Senior Member
@ Hippy;

Wouldn't this be the same?
Code:
Select Case w6
  Case 1    : If w1 < 110 Then
                Gosub LightOn
              End If
  Case 2    : If w1 < 164 Then
                Gosub LightOn
              End If
  Else   : Gosub LightOff
End Select
But even this is 6 bytes longer than the original code!

@Wapo
You might be surprised, the more complex the line is, the more memory is used as the line is converted into 'interpreter speak' for download. So even if the mixed and/or/bracketed instructions worked, they likely would not use any less program space in the chip - only a test would determine this.
By the way, the suggested line;
if (w6=1 AND w1 < 110) OR (w6=2 AND w1<164) then
fails a syntax check for a 28X1.

Just moving the original code from an 08M to a 28X1 adds 7 bytes!
 
Last edited:

hippy

Ex-Staff (retired)
No that wouldn't work; with w6=1, w1=100 the lights would be turned on, but when w1 rises to 120 there's no path whch turns the lights off. I nearly got that wrong as well.

Parenthesis in expresssions is in the pipeline but have been for a while. No idea if that's still planned for the X1, will appear with the X2 or has been shelved or delayed.

The increase in code size when moving to the X1 is for a number of reasons; four extra bits are needed to address the program memory which is 16 times as large, the encoding of instructions has been changed to be more logical and faster to execute. This adds an extra bit to many commands but also reduces the size of others. Swings and roundabouts, but overall I would expect most programs to become slightly larger when moved to an X1.

An extra 7 bytes used can be called sigificant on an 08M (3%) but is less than 0.2% of the X1's memory. All it really shows is that you cannot put a program 16 times larger than fits in an 08M ( or 4 times larger than fits in an 18X ) into an X1, just slightly less.

I've spent days trying to save a half dozen bytes on an 08M but I wouldn't even bother on an X1 as there would still be around 3,800 bytes free. My rule of thumb is that it's often reasonably easy to save 10% of code space with optimisations. That returns just 25 bytes on an 08M but potentially 400 on an X1. I'd be surprised if there were many projects which ran out of code space in an X1.
 

westaust55

Moderator
I guess the following as my own trial proves what others have been saying.

While the manual 2 page 75 for the IF...THEN GOSUB function states that:
Multiple compares can be combined with the AND and OR keywords
Multiple compares it is not reliable and needs to be avoided. Look at the following 6 simple tests using both AND and OR. Five appear to work but then it fails on the 6th which in theory should work: :confused: yet again the 7th test comes up okay :confused:
can only conclude that that like brackets, the manual is stating capabilites that do not exist . . . .

Try it in the Simulation mode for yourself . . . . .

Code:
w1=1
w2=1
w3=2
w4=2

if w1=1 or w2 =2 and w3=2 and w4=1 then pass1
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Failed")
goto test2
pass1:
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Passed")

test2:
w1=1
w2=2
w3=2
w4=2

if w1=1 or w2 =2 and w3=2 and w4=1 then pass2
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Failed")
goto test3
pass2:
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Passed")

test3:
w1=2
w2=2
w3=2
w4=1

if w1=1 or w2 =2 and w3=2 and w4=1 then pass3
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Failed")
goto test4
pass3:
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Passed")

;[B] okay, so lets  move the OR to right hand side . . . .[/B]
test4:
w1=1
w2=2
w3=2
w4=1

if w1=1 and w2 =2 and w3=2 or w4=1 then pass4
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Failed")
goto test5
pass4:
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Passed")

test5:
w1=1
w2=2
w3=2
w4=2

if w1=1 and w2 =2 and w3=2 or w4=1 then pass5
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Failed")
goto test6
pass5:
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Passed")

test6:
w1=2
w2=2
w3=2
w4=1

if w1=1 and w2 =2 and w3=2 or w4=1 then pass6
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Failed")
goto test7
pass6:
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Passed")

test7:
w1=1
w2=2
w3=1
w4=1

if w1=1 and w2 =2 and w3=2 or w4=1 then pass7
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Failed")
end
pass7:
serout 1, N2400, (#w1," ",#w2," ",#w3," ",#w4," Passed")
 
Last edited:

hippy

Ex-Staff (retired)
I agree, the simulator is screwed to buggery. It doesn't give correct answers no matter how the AND and OR are ordered.

In a perfect world the PICAXE would behave exactly as the manual describes and the manual will describe exactly how the PICAXE behaves and the Simulator will behave in exactly the same way as a genuine PICAXE will.

When behaviours disagree though you're into a deep philosophical debate as to what's right and wrong, and how right and how wrong each point on the triangle is.

The manual is technically 100% correct that AND and OR can be combined, but because such behavour is not defined ( and may differ between PICAXE and Simulator and differ to what would be expected to happen ) the recommendation to not mix is best observed.
 
Top