Retrieving data from table

GeorgeB

Member
Hi everyone

Does anyone know an efficient way of retrieving data from a lookup table like that :

Table 28, (1,1,"k")
Table (2,5,"k")
Table (3,10,"k")
Table (4,50,"k")
Table (5,100,"k")
Table (6,500,"k")
Table (7,1,"M")
Table (8,5,"M")
Table (9,10,"M")
Table (10,50,"M")
Table (11,100,"M")
Table (12,500,"M")

Table 210,(1,1,"k")
Table (2,5,"k")
Table (3,10,"k")
Table (4,50,"k")
Table (5,100,"k")
Table (6,500,"k")
Table (7,1,"M")
Table (8,5,"M")
Table (9,10,"M")
Table (10,50,"M")
Table (11,100,"M")
Table (12,500,"M")

I want to get the value of the first number, the second and the third symbol but the point is the data is inconsistent so for example if I tried getting the first address I will get 1 and 1 and "k" which means 3 bytes but if I tried getting the 500 one it would be 12,500,"M" which means 4 bytes as 500 is stored in two bytes. So does anyone know an efficient way of doing it?

Thanks in advance
 

hippy

Technical Support
Staff member
If you specify a value greater than 255 that will be truncated to 8-bits and only a byte value stored -
Code:
#Picaxe 20X2
#Terminal 9600
Table 0, ( 0,1,2,333,4,5 )
For b0 = 0 To 5
  ReadTable b0, b1
  SerTxd( "Table(",#b0,") = ", #b1, CR, LF )
Next
When run or simulated that will show "Table(3)=77" where 77 is '333 & $FF' ( or 333-256 ).

It is not possible as far as I know to split a greater than 255 number into bytes at compile time and the best approach is to always use four bytes per entry then create the actual data wanted from the data read.

The "x,yy" are decimal values "xyy" so "1,23" would represent "123". Not perfect but tolerable -
Code:
Table 28, ( 1, 0,01, "k" ) ; Entry[0]   1
Table     ( 2, 0,05, "k" ) ; Entry[1]   5
Table     ( 3, 0,10, "k" ) ; Entry[2]  10
Table     ( 4, 0,50, "k" ) ; Entry[3]  50
Table     ( 5, 1,00, "k" ) ; Enyty[4] 100
Table     ( 6, 5,00, "k" ) ; Entry[5] 500
Code:
For b0 = 0 To 5
  Gosub ReadEntry
  SerTxd( "Entry[",#b0,"] = ", #w10, " ", #w11, " ", w12, CR, LF )
Next
End

ReadEntry:
  b1 = b0 * 4 + 28
  ReadTable b1, b2,b3,b4,b5
  w10 = b2
  w11 = b3 * 100 + b4
  w12 = b5
  Return
Code:
Entry[0] = 1 1 k
Entry[1] = 2 5 k
Entry[2] = 3 10 k
Entry[3] = 4 50 k
Entry[4] = 5 100 k
Entry[5] = 6 500 k
 

hippy

Technical Support
Staff member
Table (2,5,"k")

Given the first number seems to be an index from the start, the 1,5,10,50,100,500 pattern, k and M when I guess some value is over 1000; I would expect that all the data could be calculated from the raw input without any lookup at all, or with a much simpler lookup.

If you can let us know what you are trying to achieve, what input data you have which decides the lookup, there may be an easier solution to your problem.

Added : For example -
Code:
For b0 = 0 To 21
  Gosub CalculateResistorValue
  SerTxd( #b0, " = ", #w1, w2, CR, LF )
Next
End

CalculateResistorValue:
  w2 = "R"
  w1 = b0 & 1 * 5 Min 1
  b1 = b0 / 2
  Do While b1 > 0
    w1 = w1 * 10
    b1 = b1 - 1
    If w1 >= 1000 Then
      Select Case w2
        Case "R" : w1 = w1 / 1000 : w2 = "K"
        Case "K" : w1 = w1 / 1000 : w2 = "M"
      End Select
    End If
  Loop
  Return
Code:
0 = 1R
1 = 5R
2 = 10R
3 = 50R
4 = 100R
5 = 500R
6 = 1K
7 = 5K
8 = 10K
9 = 50K
10 = 100K
11 = 500K
12 = 1M
13 = 5M
14 = 10M
15 = 50M
16 = 100M
17 = 500M
18 = 1000M
19 = 5000M
20 = 10000M
21 = 50000M
 
Last edited:

GeorgeB

Member
If you specify a value greater than 255 that will be truncated to 8-bits and only a byte value stored -
Code:
#Picaxe 20X2
#Terminal 9600
Table 0, ( 0,1,2,333,4,5 )
For b0 = 0 To 5
  ReadTable b0, b1
  SerTxd( "Table(",#b0,") = ", #b1, CR, LF )
Next
When run or simulated that will show "Table(3)=77" where 77 is '333 & $FF' ( or 333-256 ).

It is not possible as far as I know to split a greater than 255 number into bytes at compile time and the best approach is to always use four bytes per entry then create the actual data wanted from the data read.

The "x,yy" are decimal values "xyy" so "1,23" would represent "123". Not perfect but tolerable -
Code:
Table 28, ( 1, 0,01, "k" ) ; Entry[0]   1
Table     ( 2, 0,05, "k" ) ; Entry[1]   5
Table     ( 3, 0,10, "k" ) ; Entry[2]  10
Table     ( 4, 0,50, "k" ) ; Entry[3]  50
Table     ( 5, 1,00, "k" ) ; Enyty[4] 100
Table     ( 6, 5,00, "k" ) ; Entry[5] 500
Code:
For b0 = 0 To 5
  Gosub ReadEntry
  SerTxd( "Entry[",#b0,"] = ", #w10, " ", #w11, " ", w12, CR, LF )
Next
End

ReadEntry:
  b1 = b0 * 4 + 28
  ReadTable b1, b2,b3,b4,b5
  w10 = b2
  w11 = b3 * 100 + b4
  w12 = b5
  Return
Code:
Entry[0] = 1 1 k
Entry[1] = 2 5 k
Entry[2] = 3 10 k
Entry[3] = 4 50 k
Entry[4] = 5 100 k
Entry[5] = 6 500 k
Thanks for your help Hippy but I still don't quite understand what have you done there why do you have b1=b0*4+28? and w11=b3*100+b4
 

GeorgeB

Member
So the idea from my program is that I have two pics talking to each other. the control one is sending the relay index for the pos-gnd terminal and also the relay index for the neg-gnd terminal, then the slave pic sends back the relay number and the resistor value with it back to the master pic to be displayed on an OLED display. So the whole point is saving the relay numbers and their corresponding resistor values to be able to retrieve them when the master asks for it. I hope this explains what I want
 

Aries

New Member
It's a bit clunky, but you can do something like this to create the table (4 bytes per record) ...
Code:
symbol Key1 = 1          :symbol Entry1 = 1            :symbol Code1 = "k"
symbol Key2 = 12        :symbol Entry2 = 500        :symbol Code2 = "M"


symbol Entry1.lsb = Entry1 // 256
symbol Entry1.msb = Entry1 / 256
symbol Entry2.lsb = Entry2 // 256
symbol Entry2.msb = Entry2 / 256

TABLE 28,(Key1,Entry1.lsb,Entry1.msb,Code1)
TABLE (Key2,Entry2.lsb,Entry2.msb,Code2)
 

hippy

Technical Support
Staff member
Thanks for your help Hippy but I still don't quite understand what have you done there why do you have b1=b0*4+28? and w11=b3*100+b4
The 'b1=b0*4+28' was just to get the demo code reading from your table at the right location. The *4 selects each consecutive entry, the +28 is where it starts in TABLE memory. Thus b0=0 will access the first entry, b0=1 the second and so on.

The 'w11=b3*100+b4' takes two of the four bytes, the 1,23 for example, the 1 in b3, the 23 in b4, and turns it into the 123 it represents in w11.
 

AllyCat

Senior Member
Hi,

The LOOKUP command can be very useful because it can accept a mixture of small and large numbers (bytes or words), characters and even variables (e.g. b9), etc.

Or, the data you show is so "patterned" that each entry could be easily coded into a single byte. The first character is either a 1 or 5 (so a single flag bit), then 0, 1 or 2 zeros (can be coded into two bits) and a "k" or "M" (another single flag bit, or two bits to include "R" and "G").

Cheers, Alan.
 
Top