ARRAY OF NUMBERS

i have an array of numbers and i would like to know, what is the closest position that is equal or smaller than “x”

for example

x= 46

float Y[8] = {0,10,20,30,40,55,60,70};

40 is the closest smaller value

but how to tell to arduino to search the value of this position in the array ?

If you need faster, try a binary search.

Are the entries in the array always in ascending order ?

yes always is in ascending order

Not very elegant, but try:

oid setup() {
// put your setup code here, to run once:
float Y[8] = {0, 10, 20, 30, 40, 55, 60, 70};
float newDifference, oldDifference;
int index;
float target = 46.0;

Serial.begin(9600);
while (!Serial)
;

newDifference = fabs(Y[0] - target);
for (int i = 0; i < 8; i++) {
newDifference = fabs(Y[i] - target);
if (newDifference < oldDifference) {
oldDifference = newDifference;
index = i;
}
}
Serial.print("closest = ");
Serial.println(Y[index]);
}

void loop() {
}

Use std::upper_bound. Using the standard algorithms is often the fastest and easiest way. std::upper_bound uses binary search, so is faster than a manual linear for loop as presented by econjack. Since they are part of the C++ Standard Library, they are well-tested and known to be correct.
Most importantly, it is much more readable than a raw loop: any C++ programmer can immediately tell what the upper_bound line is doing, interpreting 10 lines of for-loop code takes a lot longer to read.

The iterator syntax takes some getting used to, and has been improved in C++20 (not available on Arduino yet), but you can think of std::upper_bound(std::begin(Y), std::end(Y), X) as: search from the beginning to the end of the array for X.

An iterator such as the result variable is just a variable that points to an element in an array or other data structure. To get the value of the element that the iterator points to, you use an asterisk: *result.

[color=#5e6d03]#include[/color] [color=#434f54]<[/color][b][color=#d35400]Arduino_Helpers[/color][/b][color=#434f54].[/color][color=#000000]h[/color][color=#434f54]>[/color]
[color=#5e6d03]#include[/color] [color=#434f54]<[/color][b][color=#d35400]AH[/color][/b][color=#434f54]/[/color][color=#000000]STL[/color][color=#434f54]/[/color][color=#000000]algorithm[/color][color=#434f54]>[/color] [color=#434f54]// std::sort, std::upper_bound[/color]
[color=#5e6d03]#include[/color] [color=#434f54]<[/color][b][color=#d35400]AH[/color][/b][color=#434f54]/[/color][color=#000000]STL[/color][color=#434f54]/[/color][b][color=#d35400]iterator[/color][/b][color=#434f54]>[/color]  [color=#434f54]// std::begin, std::end[/color]

[color=#00979c]void[/color] [color=#5e6d03]setup[/color][color=#000000]([/color][color=#000000])[/color] [color=#000000]{[/color]
[b][color=#d35400]Serial[/color][/b][color=#434f54].[/color][color=#d35400]begin[/color][color=#000000]([/color][color=#000000]115200[/color][color=#000000])[/color][color=#000000];[/color]

[color=#00979c]float[/color] [color=#000000]Y[/color][color=#000000][[/color][color=#000000]8[/color][color=#000000]][/color] [color=#434f54]=[/color] [color=#000000]{[/color][color=#000000]0[/color][color=#434f54],[/color][color=#000000]10[/color][color=#434f54],[/color][color=#000000]20[/color][color=#434f54],[/color][color=#000000]30[/color][color=#434f54],[/color][color=#000000]40[/color][color=#434f54],[/color][color=#000000]55[/color][color=#434f54],[/color][color=#000000]60[/color][color=#434f54],[/color][color=#000000]70[/color][color=#000000]}[/color][color=#000000];[/color]
[color=#00979c]float[/color] [color=#000000]X[/color] [color=#434f54]=[/color] [color=#000000]46[/color][color=#000000];[/color]
[color=#434f54]// Ensure all elements are sorted:[/color]
[color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#000000]sort[/color][color=#000000]([/color][color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]begin[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#434f54],[/color] [color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]end[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#000000])[/color][color=#000000];[/color]
[color=#434f54]// Find the first element that's larger than X, and subtract one[/color]
[color=#434f54]// to get the one before it (result is an iterator to the element):[/color]
[color=#00979c]auto[/color] [color=#000000]result[/color] [color=#434f54]=[/color] [color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#000000]upper_bound[/color][color=#000000]([/color][color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]begin[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#434f54],[/color] [color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]end[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#434f54],[/color] [color=#000000]X[/color][color=#000000])[/color] [color=#434f54]-[/color] [color=#000000]1[/color][color=#000000];[/color]
[color=#00979c]auto[/color] [color=#000000]index[/color] [color=#434f54]=[/color] [color=#000000]result[/color] [color=#434f54]-[/color] [color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]begin[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#000000];[/color]
[color=#5e6d03]if[/color] [color=#000000]([/color][color=#000000]index[/color] [color=#434f54]<[/color] [color=#000000]0[/color][color=#000000])[/color] [color=#000000]{[/color]
[color=#000000]}[/color] [color=#5e6d03]else[/color] [color=#000000]{[/color]
[b][color=#d35400]Serial[/color][/b][color=#434f54].[/color][color=#d35400]println[/color][color=#000000]([/color][color=#000000]index[/color][color=#000000])[/color][color=#000000];[/color]
[b][color=#d35400]Serial[/color][/b][color=#434f54].[/color][color=#d35400]println[/color][color=#000000]([/color][color=#434f54]*[/color][color=#000000]result[/color][color=#000000])[/color][color=#000000];[/color]
[color=#000000]}[/color]
[color=#000000]}[/color]

[color=#00979c]void[/color] [color=#5e6d03]loop[/color][color=#000000]([/color][color=#000000])[/color] [color=#000000]{[/color][color=#000000]}[/color]

If you’re using an ARM-based or ESP-based Arduino, simply use #include and #include , they are already installed.
If you’re using an AVR-based Arduino, you’ll have to install them through the Arduino Helpers library or the ArduinoSTL library.

Pieter

econjack:
Not very elegant, but try.

Closest smaller value.

Ignoring they are in any kind of order…

int8_t found_i = -1;
for (int8_t i = 0; i < 8; i++)
{
if (Y[i] < X && (found_i == -1 || Y[i] > Y[found_i])) found_i = i;
}

found_i will be -1 on exit if there wasn’t a number less than X.

pcbbc:
Closest smaller value.

When I ran my code, it selects 40, which is the closest smaller number.

econjack:
Not very elegant, but try:

oid setup() {

// put your setup code here, to run once:
float Y[8] = {0, 10, 20, 30, 40, 55, 60, 70};
float newDifference, oldDifference;
int index;
float target = 46.0;

Serial.begin(9600);
while (!Serial)
;

newDifference = fabs(Y[0] - target);
for (int i = 0; i < 8; i++) {
newDifference = fabs(Y[i] - target);
if (newDifference < oldDifference) {
oldDifference = newDifference;
index = i;
}
}
Serial.print("closest = ");
Serial.println(Y[index]);
}

void loop() {
}

oldDifference is used before it’s initialized, and using fabs implies that it doesn’t search for the closest number less than the target.

Which kind of proves my point: all unnecessary algorithms you implement yourself are prone to errors, use the standard library algorithms instead, they’re there for a reason.

PieterP:
Which kind of proves my point: all unnecessary algorithms you implement yourself are prone to errors, use the standard library algorithms instead, they’re there for a reason.

Whilst I agree to a certain extent, for someone starting out (and someone who is uncertain about correct use of the caps lock key), learning the language and the libraries is just overload, and likely to be off-putting.

Better, IMO, is to learn the outline of the necessary techniques first.

i have an array of numbers and i would like to know, what is the closest position that is equal or smaller than “x”

Since the array is always in an ascending order its pretty simple if you test the values from large to small.

void setup() {
Serial.begin(115200);
float x = 46;
float Y[8] = {0, 10, 20, 30, 40, 55, 60, 70};
for (byte i = 7; i >= 0 ; i--)//check larger values first
{
if (Y[i] <= x)
{
Serial.print("First array value less than x is  ");
Serial.println(Y[i]);
break; //exit test loop
}
}
}
void loop() {}

for (byte i = 7; i >= 0 Close… (this ain’t Java)

TheMemberFormerlyKnownAsAWOL:
Whilst I agree to a certain extent, for someone starting out (and someone who is uncertain about correct use of the caps lock key), learning the language and the libraries is just overload, and likely to be off-putting.

Better, IMO, is to learn the outline of the necessary techniques first.

True, there's nothing wrong with implementing some basic algorithms to learn about for-loops and general programming techniques.
The problem is that many people keep doing that when they start writing serious code. They need to find an element in a sorted array, so they quickly implement their own binary search, for instance. It doesn't help that over half of the google results for "c++ binary search" are manual implementations.
Just looking at this thread alone, it's clear that even experienced programmers make mistakes in relatively simple code.

That's why I think it's a good idea to point to the right algorithms in forum threads like these.
Learning the necessary techniques is definitely important, I fully agree with you there, but I don't think an online forum is the right tool for that, you'll learn much more by following a more structured guide like a book or a course/tutorial, doing the exercises that it comes with, etc.

for (byte i = 7; i >= 0
Close… (this ain’t Java)

Oops. Reflexive use of smallest variable size. Creates a problem if number tested is out of range on the low side.

for (int i = 7; i >= 0 ; i--)

Alternatively:

for (uint8_t i = 8; i-- > 0;)
for (int8_t i = 7; i >= 0; --i)

PieterP:
Alternatively:

for (uint8_t i = 8; i-- > 0;)
for (int8_t i = 7; i >= 0; --i)

I like to think of it as a "goes to" operator:

for (uint8_t i = 8; i --> 0;)

Hello PieterP

Thank you very much for the information and sharing the librarys and the code , works perfectky

but i want to know if i can make also the inverse logic , i mean , to find the 2 next highest numbers

thanks and regards

Pieter
[/quote]

Hello PieterP

Thank you very much for the information and sharing the librarys and the code , works perfectky

but i want to know if i can make also the inverse logic , i mean , to find the 2 next highest numbers

thanks and regards

pichy:
Hello PieterP

Thank you very much for the information and sharing the librarys and the code , works perfectky

but i want to know if i can make also the inverse logic , i mean , to find the 2 next highest numbers

thanks and regards

You can use std::upper_bound again. It returns an iterator to the first element that’s larger than X. If you want the next highest number, you add one to the iterator. In this case, you have to make sure not to go out of bounds on the array:

[color=#00979c]float[/color] [color=#000000]Y[/color][color=#000000][[/color][color=#000000]8[/color][color=#000000]][/color] [color=#434f54]=[/color] [color=#000000]{[/color][color=#000000]0[/color][color=#434f54],[/color][color=#000000]10[/color][color=#434f54],[/color][color=#000000]20[/color][color=#434f54],[/color][color=#000000]30[/color][color=#434f54],[/color][color=#000000]40[/color][color=#434f54],[/color][color=#000000]55[/color][color=#434f54],[/color][color=#000000]60[/color][color=#434f54],[/color][color=#000000]70[/color][color=#000000]}[/color][color=#000000];[/color]
[color=#00979c]float[/color] [color=#000000]X[/color] [color=#434f54]=[/color] [color=#000000]46[/color][color=#000000];[/color]
[color=#434f54]// Ensure all elements are sorted:[/color]
[color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#000000]sort[/color][color=#000000]([/color][color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]begin[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#434f54],[/color] [color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]end[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#000000])[/color][color=#000000];[/color]
[color=#434f54]// Find the first element that's larger than X[/color]
[color=#00979c]auto[/color] [color=#000000]larger1[/color] [color=#434f54]=[/color] [color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#000000]upper_bound[/color][color=#000000]([/color][color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]begin[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#434f54],[/color] [color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]end[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#434f54],[/color] [color=#000000]X[/color][color=#000000])[/color][color=#000000];[/color]
[color=#5e6d03]if[/color] [color=#000000]([/color][color=#000000]larger1[/color] [color=#434f54]<[/color] [color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]end[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#000000])[/color] [color=#000000]{[/color] [color=#434f54]// don't go past the end of the array[/color]
[b][color=#d35400]Serial[/color][/b][color=#434f54].[/color][color=#d35400]println[/color][color=#000000]([/color][color=#434f54]*[/color][color=#000000]larger1[/color][color=#000000])[/color][color=#000000];[/color]
[color=#00979c]auto[/color] [color=#000000]larger2[/color] [color=#434f54]=[/color] [color=#000000]larger1[/color] [color=#434f54]+[/color] [color=#000000]1[/color][color=#000000];[/color]
[color=#5e6d03]if[/color] [color=#000000]([/color][color=#000000]larger2[/color] [color=#434f54]<[/color] [color=#000000]std[/color][color=#434f54]:[/color][color=#434f54]:[/color][color=#d35400]end[/color][color=#000000]([/color][color=#000000]Y[/color][color=#000000])[/color][color=#000000])[/color] [color=#000000]{[/color] [color=#434f54]// don't go past the end of the array[/color]
[b][color=#d35400]Serial[/color][/b][color=#434f54].[/color][color=#d35400]println[/color][color=#000000]([/color][color=#434f54]*[/color][color=#000000]larger2[/color][color=#000000])[/color][color=#000000];[/color]
[color=#000000]}[/color]
[color=#000000]}[/color] [color=#5e6d03]else[/color] [color=#000000]{[/color]