458,088 Members | 1,296 Online Need help? Post your question and get tips & solutions from a community of 458,088 IT Pros & Developers. It's quick & easy.

# TAking the minimum of three values

 P: n/a I need to find a minimum of three float values.. what would be the most efficient way of doing this? Can someone please share a #define macro or something with me for doing this? Thanks Sona Jul 19 '05 #1
28 Replies

 P: n/a "Sona" wrote in message news:3f********@clarion.carno.net.au... I need to find a minimum of three float values.. what would be the most efficient way of doing this? Can someone please share a #define macro or something with me for doing this? Thanks Sona x = min( a, min( b, c ) ); -Howard Jul 19 '05 #2

 P: n/a Sona wrote: I need to find a minimum of three float values.. what would be the most efficient way of doing this? Can someone please share a #define macro or something with me for doing this? Thanks In C++ #include double min3(double a, double b, double c) { return std::min(a, std::min(b, c)); } Jul 19 '05 #3

 P: n/a > #include double min3(double a, double b, double c) { return std::min(a, std::min(b, c)); } To keep the templated aspect of min, you could even write namespace { template T& min(T const& a, T const& b, T const& c) { return min(a, min(b,c)); } } Like that std::min works with any type, and with 2 or 3 arguments Jul 19 '05 #4

 P: n/a Sona wrote: I need to find a minimum of three float values.. what would be the most efficient way of doing this? Can someone please share a #define macro or something with me for doing this? Thanks Sona Sona, Thank you for your post. --Steve #include float min(float h, float j); int main() { float a, b, c; printf("Enter three float values, separated by spaces: "); scanf("%f%f%f", &a, &b, &c); /* * NOTE: I had to round the floats off to two decimal places * in the following printf statement, because I was getting * weird errors otherwise. */ printf("The minimum of these three is %.2f\n", min(a, min(b, c))); return 0; } float min(float h, float j) { if (h < j) return h; else return j; } Jul 19 '05 #5

 P: n/a "Howard" wrote in message news:... "Sona" wrote in message news:3f********@clarion.carno.net.au... I need to find a minimum of three float values.. what would be the most efficient way of doing this? Can someone please share a #define macro or something with me for doing this? Thanks Sona x = min( a, min( b, c ) ); Given a typical definition of min(), that will not produce an efficient result. #define min3(a,b,c) \ ( (a) < (b) ? min(a,c) : min(b,c) ) -- Peter Jul 19 '05 #6

 P: n/a Peter Nilsson wrote: "Howard" wrote in message news:... x = min( a, min( b, c ) ); Given a typical definition of min(), that will not produce an efficient result. #define min3(a,b,c) \ ( (a) < (b) ? min(a,c) : min(b,c) ) Have you counted the number of evaluations of a or b this involves? There is a good reason for preferring functions over defines. -- Martin Ambuhl Jul 19 '05 #7

 P: n/a Martin Ambuhl wrote:Peter Nilsson wrote: #define min3(a,b,c) \ ( (a) < (b) ? min(a,c) : min(b,c) )Have you counted the number of evaluations of a or b this involves? Thereis a good reason for preferring functions over defines. Not to mention possible side effects; consider: float m3, x, y, z; m3 = min3( x *= 3.142, y /= 2.718, z += 1.111 ); Irrwahn -- Computer: a million morons working at the speed of light. Jul 19 '05 #8

 P: n/a "Sona" wrote in message news:3f********@clarion.carno.net.au... I need to find a minimum of three float values.. what would be the most efficient way of doing this? Can someone please share a #define macro or something with me for doing this? Thanks Sona You want a macro. Here you go: #define min3(x, y, z) \ ((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : (((x) < (z)) ? (x) : (((y) < (z)) ? (z) : (y))) You can't beat that for efficiency. Of course it is totally unreadable. But you asked for it :-) Carsten Hansen Jul 19 '05 #9

 P: n/a Carsten Hansen wrote: "Sona" wrote in message news:3f********@clarion.carno.net.au...I need to find a minimum of three float values.. what would be the mostefficient way of doing this? Can someone please share a #define macro orsomething with me for doing this? Thanks You want a macro. Here you go: #define min3(x, y, z) \ ((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : (((x) < (z)) ? (x) : (((y) < (z)) ? (z) : (y))) You can't beat that for efficiency. It is not even correct. float min3(float x, float y, float z) { if (x < y) if (x < z) return x; if (y < z) return y; return z; } Jirka Jul 19 '05 #10

 P: n/a "Jirka Klaue" wrote in message news:bj**********@mamenchi.zrz.TU-Berlin.DE... Carsten Hansen wrote: "Sona" wrote in message news:3f********@clarion.carno.net.au...I need to find a minimum of three float values.. what would be the mostefficient way of doing this? Can someone please share a #define macro orsomething with me for doing this? Thanks You want a macro. Here you go: #define min3(x, y, z) \ ((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : (((x) < (z)) ? (x) : (((y) < (z)) ? (z) : (y))) You can't beat that for efficiency. It is not even correct. float min3(float x, float y, float z) { if (x < y) if (x < z) return x; if (y < z) return y; return z; } Jirka Give an example where it fails. Carsten Hansen Jul 19 '05 #11

 P: n/a "Ron Natalie" wrote in message news:3f***********************@news.newshosting.co m... Sona wrote: I need to find a minimum of three float values.. what would be the most efficient way of doing this? Can someone please share a #define macro or something with me for doing this? Thanks In C++ #include double min3(double a, double b, double c) { return std::min(a, std::min(b, c)); } Please do not post off-topic things here. It waste the bandwidth and time. -- Jeff Jul 19 '05 #12

 P: n/a "Jeff" wrote:"Ron Natalie" wrote in messagenews:3f***********************@news.newshosting.c om... In C++ #include double min3(double a, double b, double c) { return std::min(a, std::min(b, c)); } Please do not post off-topic things here. It waste the bandwidth and time. Erm, (almost) the whole thread is cross-posted between c.l.c and c.l.c++ -- Computer: a million morons working at the speed of light. Jul 19 '05 #13

 P: n/a Carsten Hansen wrote:"Jirka Klaue" wrote:Carsten Hansen wrote:"Sona" wrote:I need to find a minimum of three float values.. what would be the mostefficient way of doing this? Can someone please share a #define macro orsomething with me for doing this? ThanksYou want a macro. Here you go:#define min3(x, y, z) \((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : (((x) < (z))? (x) : (((y) < (z)) ? (z) : (y)))You can't beat that for efficiency.It is not even correct. Give an example where it fails. #include #define MIN3(x, y, z) \ ((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : (((x) < (z)) ? (x) : (((y) < (z)) ? (z) : (y))) int main(void) { float a = 1.6, b = 1.7, c = 1.8; printf("%f\n", MIN3(a, b, c)); a = 1.9, b = 1.7, c = 1.8; printf("%f\n", MIN3(a, b, c)); a = 1.6, b = 1.7, c = 1.5; printf("%f\n", MIN3(a, b, c)); return 0; } 1.700000 1.800000 1.600000 Now, give an example where it works. And even when you fix it, it probably is not the most efficient method. Jirka Jul 19 '05 #14

 P: n/a Carsten Hansen wrote: "Jirka Klaue" wrote in message news:bj**********@mamenchi.zrz.TU-Berlin.DE...Carsten Hansen wrote:"Sona" wrote in messagenews:3f********@clarion.carno.net.au... I need to find a minimum of three float values.. what would be the mostefficient way of doing this? Can someone please share a #define macro orsomething with me for doing this? ThanksYou want a macro. Here you go:#define min3(x, y, z) \((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : (((x) < (z))? (x) : (((y) < (z)) ? (z) : (y)))You can't beat that for efficiency.It is not even correct.float min3(float x, float y, float z){ if (x < y) if (x < z) return x; if (y < z) return y; return z;}Jirka Give an example where it fails. Carsten Hansen Carsten, Thank you for your post. I don't intend this post as mean-spirited; I cannot write such a macro. #include #define min3(x, y, z) \ ((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : \ (((x) < (z)) ? (x) : (((y) < (z)) ? (z) : (y))) int main() { float x, y, z; printf("Enter three float values, separated by spaces: "); scanf("%f%f%f", &x, &y, &z); printf("The least of these is %f\n", min3(x, y, z)); return 0; } Input from keyboard: 12345 44444 55555 Output to screen: The least of these is 44444 Jul 19 '05 #15

 P: n/a On Wed, 10 Sep 2003 04:34:29 +1000, Sona wrote: I need to find a minimum of three float values.. what would be the mostefficient way of doing this? Can someone please share a #define macro orsomething with me for doing this? Thanks First off, DO NOT, I repeat for your convenience, DO NOT, crosspost general questions to both [comp.lang.c] and [comp.lang.c++]. Those are different languages. Now _the_ (one and only) answer to your question is simple: the _most efficient_ way of finding the minimum of three 'double' values is to leverage contextual information and language- and implementation- quirks. That depends very much on the problem to be solved, your current code, the language you're using, and even the compiler. Post this information, except the compiler, and you may receive more specific answers. Jul 19 '05 #16

 P: n/a "Jirka Klaue" wrote in message news:bj**********@mamenchi.zrz.TU-Berlin.DE... Carsten Hansen wrote:"Jirka Klaue" wrote:Carsten Hansen wrote:"Sona" wrote:>I need to find a minimum of three float values.. what would be the most>efficient way of doing this? Can someone please share a #define macro or>something with me for doing this? ThanksYou want a macro. Here you go:#define min3(x, y, z) \((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : (((x) < (z))? (x) : (((y) < (z)) ? (z) : (y)))You can't beat that for efficiency.It is not even correct. Give an example where it fails. #include #define MIN3(x, y, z) \ ((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : (((x) < (z)) ? (x) : (((y) < (z)) ? (z) : (y))) int main(void) { float a = 1.6, b = 1.7, c = 1.8; printf("%f\n", MIN3(a, b, c)); a = 1.9, b = 1.7, c = 1.8; printf("%f\n", MIN3(a, b, c)); a = 1.6, b = 1.7, c = 1.5; printf("%f\n", MIN3(a, b, c)); return 0; } 1.700000 1.800000 1.600000 Now, give an example where it works. And even when you fix it, it probably is not the most efficient method. Jirka Sorry. It is me being stupid. The macro I posted returns the median of the three, not the minimum. This one is much simpler. #define min3(x, y, z) \ (((x) < (y)) ? (((z) < (x)) ? (z) : (x)) : (((z) < (y)) ? (z) : (y))) Carsten Hansen Jul 19 '05 #17

 P: n/a Carsten Hansen wrote: ....>#define min3(x, y, z) \>((x) < (y)) ? (((y) < (z)) ? (y) : (((x) < (z)) ? (z) : (x))) : (((x) < (z)) ? (x) : (((y) < (z)) ? (z) : (y))) .... Sorry. It is me being stupid. The macro I posted returns the median of the three, not the minimum. This one is much simpler. #define min3(x, y, z) \ (((x) < (y)) ? (((z) < (x)) ? (z) : (x)) : (((z) < (y)) ? (z) : (y))) I see. Seems to be pretty efficient now, too. :-) Jirka Jul 19 '05 #18

 P: n/a Martin Ambuhl wrote in message news:... Peter Nilsson wrote: "Howard" wrote in message news:...x = min( a, min( b, c ) ); Given a typical definition of min(), that will not produce an efficient result. #define min3(a,b,c) \ ( (a) < (b) ? min(a,c) : min(b,c) ) Have you counted the number of evaluations of a or b this involves? There is a good reason for preferring functions over defines. Inline functions yes; but functions, in C, not always. My problem was not realising that the OP cross posted. My Bad. I was reading it in clc and concentrated on "Can someone please share a #define macro or something..." in the OP's post. [I really don't know why people using C++ also ask C groups for solutions when the answers are highly likely to involve different paradigms and/or language constructs.] Anyway, my mistake... FWIW, C99 has its own version of inline functions too. -- Peter Jul 19 '05 #19

 P: n/a "Peter Nilsson" wrote in message news:63**************************@posting.google.c om... x = min( a, min( b, c ) ); Given a typical definition of min(), that will not produce an efficient result. #define min3(a,b,c) \ ( (a) < (b) ? min(a,c) : min(b,c) ) The typical min is inlined to something like a < b ? a : b There's always two comparisons. Tests show no speed difference between the two on my machine. Jul 19 '05 #20

 P: n/a On Wed, 10 Sep 2003, Ron Natalie wrote: "Peter Nilsson" wrote... x = min( a, min( b, c ) ); Given a typical definition of min(), that will not produce an efficient result. #define min3(a,b,c) \ ( (a) < (b) ? min(a,c) : min(b,c) ) The typical min is inlined to something like a < b ? a : b There's always two comparisons. Tests show no speed difference between the two on my machine. Are you using functions, or macros? I'm sure that Peter was referring to the use of macros, in C -- *not* C++, for the benefit of those reading in c.l.c++. So we have, without the usual parentheses since they'd just clutter the example: #define min(a,b) ((a < b)? a: b) #define min3_inefficient(a,b,c) min(a, min(b, c)) #define min3_better(a,b,c) (a < b)? min(a, c): min(b, c) min3_inefficient(X, Y, Z) becomes min(X, ((Y < Z)? Y: Z)) ((X < ((Y < Z)? Y: Z))? X: ((Y < Z)? Y: Z))) min3_better(X, Y, Z) becomes ((X < Y)? ((X < Z)? X: Z): (Y < Z)? Y: Z) In this case, even though both expansions contain the same number of < and ? characters, the "inefficient" version has poorer control flow -- three conditionals are evaluated fully 2/3 of the time, whereas with the "better" version only two conditionals are ever executed. With C++ template functions, of course, it doesn't matter so much. But if you're interested in efficiency, why are you using functions? ;-) -Arthur Jul 19 '05 #21

 P: n/a Irrwahn Grausewitz writes: "Jeff" wrote:Please do not post off-topic things here. It waste the bandwidth and time. Erm, (almost) the whole thread is cross-posted between c.l.c and c.l.c++ So any proposed solutions should work in both C and C++. -- "...deficient support can be a virtue. It keeps the amateurs off." --Bjarne Stroustrup Jul 19 '05 #22

 P: n/a Ben Pfaff wrote: Irrwahn Grausewitz writes: "Jeff" wrote: >Please do not post off-topic things here. It waste the bandwidth and time. Erm, (almost) the whole thread is cross-posted between c.l.c and c.l.c++So any proposed solutions should work in both C and C++. And one who is cross-posting complaints about off-topicality of cross-posted replies to cross-posted questions should make clear what the word "here" is referring to in this context. -- What does this red button do? Jul 19 '05 #23

 P: n/a "Arthur J. O'Dwyer" wrote in message news:Pine.LNX.4.55L- Are you using functions, or macros? I'm sure that Peter was referring to the use of macros, in C -- *not* C++, for the benefit of those reading in c.l.c++. I used inline functions. It's even worse if he used macros as the expressions passed are possibly evaluated more than once. In this case, even though both expansions contain the same number of < and ? characters, the "inefficient" version has poorer control flow -- three conditionals are evaluated fully 2/3 of the time, whereas with the "better" version only two conditionals are ever executed. It's beyond me what you mean by that. Both times execute the comparison twice, as a result the select. You can make up your own idea of the cost of the flow between the two, but as I said, it;s negligable. Both functions on the Sun compiler take the same amount of time. With C++ template functions, of course, it doesn't matter so much. But if you're interested in efficiency, why are you using functions? ;-) Templates have no bearing on this situation at all. You could as easily code this as functions taking doubles without templates and the answer would be the same. Jul 19 '05 #24

 P: n/a "Arthur J. O'Dwyer" wrote in message news:Pi************************************@unix49 .andrew.cmu.edu... (snip) Are you using functions, or macros? I'm sure that Peter was referring to the use of macros, in C -- *not* C++, for the benefit of those reading in c.l.c++. So we have, without the usual parentheses since they'd just clutter the example: #define min(a,b) ((a < b)? a: b) #define min3_inefficient(a,b,c) min(a, min(b, c)) #define min3_better(a,b,c) (a < b)? min(a, c): min(b, c) min3_inefficient(X, Y, Z) becomes min(X, ((Y < Z)? Y: Z)) ((X < ((Y < Z)? Y: Z))? X: ((Y < Z)? Y: Z))) min3_better(X, Y, Z) becomes ((X < Y)? ((X < Z)? X: Z): (Y < Z)? Y: Z) In this case, even though both expansions contain the same number of < and ? characters, the "inefficient" version has poorer control flow -- three conditionals are evaluated fully 2/3 of the time, whereas with the "better" version only two conditionals are ever executed. Good compilers do common subexpression elimination, and hopefully will notice that (Y

 P: n/a On Wed, 10 Sep 2003, Ron Natalie wrote: "Arthur J. O'Dwyer" wrote... Are you using functions, or macros? I'm sure that Peter was referring to the use of macros, in C -- *not* C++, for the benefit of those reading in c.l.c++. I used inline functions. It's even worse if he used macros as the expressions passed are possibly evaluated more than once. True; however, he did mention the *usual* definition of 'min', which IME is more often than not as a macro. In this case, even though both expansions contain the same number of < and ? characters, the "inefficient" version has poorer control flow -- three conditionals are evaluated fully 2/3 of the time, whereas with the "better" version only two conditionals are ever executed. It's beyond me what you mean by that. Both times execute the comparison twice, as a result the select. Brain fart? :-) Unsnipped from my previous post: min3_inefficient(X, Y, Z) becomes min(X, ((Y < Z)? Y: Z)) ((X < ((Y < Z)? Y: Z))? X: ((Y < Z)? Y: Z))) min3_better(X, Y, Z) becomes ((X < Y)? ((X < Z)? X: Z): (Y < Z)? Y: Z) Suppose X is the least of the three... then min3_inefficient compares Y to Z then compares X to min(Y,Z) min3_better compares X to Y then compares X to Z Suppose Y is the least of the three... then min3_inefficient compares Y to Z then compares X to Y then compares Y to Z min3_better compares X to Y then compares Y to Z Suppose Z is the least of the three... then min3_inefficient compares Y to Z then compares X to Z then compares Y to Z min3_better compares X to Y then compares min(X,Y) to Z See? min3_better makes exactly 2 comparisons in each case, while min3_inefficient makes 3 comparisons fully 2/3 of the time, as I said. Thus min3_inefficient *is* less efficient, because it computes useless comparisons. You can make up your own idea of the cost of the flow between the two, but as I said, it;s negligable. Both functions on the Sun compiler take the same amount of time. Try running them more than once. (But before doing that, take a look at the generated machine code. I would not be surprised if the GCC folks have optimized this particular computation, so the Sun folks might have too.) With C++ template functions, of course, it doesn't matter so much. But if you're interested in efficiency, why are you using functions? ;-) Templates have no bearing on this situation at all. You could as easily code this as functions taking doubles without templates and the answer would be the same. ....except in the case where you wanted to compare pointers. Or C++ std::strings. Or 'long longs'. Or practically anything that wasn't a double. (Which, incidentally, is why the most common implementation of 'min' is as a macro -- because C macros can do things that C functions can't.) -Arthur Jul 19 '05 #26

 P: n/a "Arthur J. O'Dwyer" wrote in message news:Pi***********************************@unix45. andrew.cmu.edu... On Wed, 10 Sep 2003, Ron Natalie wrote: "Arthur J. O'Dwyer" wrote... Are you using functions, or macros? I'm sure that Peter was referring to the use of macros, in C -- *not* C++, for the benefit of those reading in c.l.c++. I used inline functions. It's even worse if he used macros as the expressions passed are possibly evaluated more than once. True; however, he did mention the *usual* definition of 'min', which IME is more often than not as a macro. Maybe it is in C, but it certainly IS NOT in C++. See? min3_better makes exactly 2 comparisons in each case, while min3_inefficient makes 3 comparisons fully 2/3 of the time, as I said. Thus min3_inefficient *is* less efficient, because it computes useless comparisons. It is for the ugly macros, as I was saying, for inline functions it does not need to generate a bogus third test. Jul 19 '05 #27

 P: n/a Ron Natalie wrote: "Arthur J. O'Dwyer" wrote in message news:Pi***********************************@unix45. andrew.cmu.edu... On Wed, 10 Sep 2003, Ron Natalie wrote: "Arthur J. O'Dwyer" wrote... > Are you using functions, or macros? I'm sure that Peter > was referring to the use of macros, in C -- *not* C++, for > the benefit of those reading in c.l.c++. I used inline functions. It's even worse if he used macros as the expressions passed are possibly evaluated more than once. True; however, he did mention the *usual* definition of 'min', which IME is more often than not as a macro. Maybe it is in C, but it certainly IS NOT in C++. The following macro is a paradigm in C: #define max(a, b) ((a) > (b) ? (a) : (b)) -- pete Jul 19 '05 #28

 P: n/a Arthur J. O'Dwyer wrote: On Wed, 10 Sep 2003, Ron Natalie wrote: "Peter Nilsson" wrote... > x = min( a, min( b, c ) ); Given a typical definition of min(), that will not produce an efficient result. #define min3(a,b,c) \ ( (a) < (b) ? min(a,c) : min(b,c) ) The typical min is inlined to something like a < b ? a : b There's always two comparisons. Tests show no speed difference between the two on my machine. Are you using functions, or macros? I'm sure that Peter was referring to the use of macros, in C -- *not* C++, for the benefit of those reading in c.l.c++. So we have, without the usual parentheses since they'd just clutter the example: #define min(a,b) ((a < b)? a: b) It's illogical to remove required parentheses and then insert extra one's that you like. Minimally but correctly parenthesized: #define min(a, b) ((b) > (a) ? a : (b)) -- pete Jul 19 '05 #29

### This discussion thread is closed

Replies have been disabled for this discussion.

### Similar topics

Browse more C / C++ Questions on Bytes 