Skip to content

Sensors & Signal Processing

How to linearise a sensor with a lookup table

To turn a curved sensor reading into real units, measure the sensor at known points, store the pairs in a lookup table, find the two entries a new reading falls between, and draw a straight line across just that band. That's linear interpolation. The curve may bend, but over any short band it's nearly straight.

Why one line isn't enough

A thermistor in a voltage divider gives a reading that falls as it warms, steeply when cold and gently when hot. At 0 °C this one reads 788; at 100 °C, 67. A single straight line through those two ends, which is what map() draws, is out by about 22 degrees in the middle, near 52 °C.

The table

Measure it once every 10 degrees:

°C0102030405060708090100
Reading7886845694563542702041531158767

Interpolate across the band

T = TEMP[i] + (RAW[i] − raw) × 10 ÷ (RAW[i] − RAW[i + 1])

A reading of 520 falls between 569 (20 °C) and 456 (30 °C). It's (569 − 520) ÷ (569 − 456) = 49 ÷ 113 = 0.43 of the way across, so the temperature is 20 + 4.3 = 24.3 °C.

const int  RAW[11]  = {788, 684, 569, 456, 354, 270, 204, 153, 115, 87, 67};
const float TEMP[11] = {0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100};

float celsius(int raw) {
  if (raw >= RAW[0]) return 0;                 // colder than the table
  for (int i = 0; i < 10; i++) {
    if (raw >= RAW[i + 1]) {                   // in band i
      return TEMP[i] + (RAW[i] - raw) * 10.0 / (RAW[i] - RAW[i + 1]);
    }
  }
  return 100;                                  // hotter than the table
}

Live experiment

Straighten a thermistor curve

A thermistor warms from 0 to 100 °C and its reading falls from 788 to 67 along a curve. Convert it three ways and watch the error: one straight line through the ends is out by 22 degrees, the table alone by 10, the table with interpolation by about 1.2.

Try it yourself: free lesson

“Lookup tables” is lesson 2 of 5 in Dither Delta, Sensors & Signal Processing World 2. Free with an account. Lessons unlock in order, so you’ll do the 8 before it first.

How good is it?

MethodWorst error
One straight line, end to endabout 22 °C
Table, answering each band's bottom edgeabout 10 °C
Table with interpolationabout 1.2 °C

Tips

  • The reading falls as the temperature rises, so band i is where RAW[i] ≥ raw ≥ RAW[i + 1]. A rising sensor flips the test.
  • Decide what to return off the ends of the table, and treat a reading far off the ends as a possible fault.
  • Points don't have to be evenly spaced. Crowd them where the curve bends.

Car engine computers look up fuel and ignition timing this way hundreds of times a second, and so do colour profiles on screens and synthesizers' wave tables.

Free lesson

Now build it yourself

Each lesson comes in three short parts: see the idea, try it on a live board, then build it yourself, with quick checks as you go.

Try it yourself: free lesson

“Lookup tables” is lesson 2 of 5 in Dither Delta, Sensors & Signal Processing World 2. Free with an account. Lessons unlock in order, so you’ll do the 8 before it first.

Or start from the very first lesson, no account needed

Practice questions

Three quick questions from the lessons. Pick an answer to check it.

  1. Question 1 of 3RAW falls as the temperature rises. The reading is in band i when…
    Show the answer

    Answer: RAW[i] ≥ raw ≥ RAW[i + 1]. Readings get smaller as it warms, so each band runs from a bigger number down to a smaller one.

    • Why not “raw > RAW[0]”? A reading above RAW[0] is off the cold end of the table, not inside any band.
    • Why not “raw == RAW[i]”? Only readings exactly on a table point would match. Every reading between points would be missed.
    • Why not “RAW[i] ≤ raw ≤ RAW[i + 1]”? That's the test for a table that rises with temperature. Here each band runs from a bigger number down to a smaller one.
  2. Question 2 of 3map(raw, RAW[0], RAW[10], 0, 100) gives…
    Show the answer

    Answer: One straight line end to end: out by 20 degrees in the middle. map() is linear interpolation across the whole range: one band. The curve needs ten.

    • Why not “The same as the table”? map() uses only the two end points, so it can't follow the curve between them.
    • Why not “An error”? map() runs fine on these numbers. It just draws one straight line across a curve.
    • Why not “The right answer”? It's right only at the two ends. In the middle the curve sags far from the straight line.
  3. Question 3 of 3Linear interpolation in a table draws a straight line…
    Show the answer

    Answer: Between the two table entries a reading falls between. Short straight lines between neighbours, one band at a time.

    • Why not “Through the whole range”? That's a single straight line, which is what the table is there to avoid.
    • Why not “From zero”? Nothing ties the line to zero; it runs between the two neighbouring table points.
    • Why not “Nowhere”? Interpolation is exactly a straight line, just a short one across one band.
Keep practising: free lesson

“Lookup tables” is lesson 2 of 5 in Dither Delta, Sensors & Signal Processing World 2. Free with an account. Lessons unlock in order, so you’ll do the 8 before it first.

Questions people ask

Why use a lookup table instead of the Steinhart-Hart equation?

Steinhart-Hart needs a logarithm and a cube, which a small microcontroller computes slowly. A table with interpolation takes a few multiplications, and works for any sensor curve, even one with no formula at all, as long as you can measure it.

How many points does a lookup table need?

Enough that the curve is nearly straight between neighbours. Eleven points, every 10 degrees, bring a thermistor within about 1.2 degrees. Put extra points where the curve bends hardest, since that's where straight lines between points are worst.

Can I use Arduino's map() between table points?

Yes: map() is linear interpolation across one band. But it works in whole numbers and rounds down, so for a fractional answer write the formula yourself with floating-point maths.

Every topic