On some rare machines where branching is expensive, the below obvious approach to find minimum can be slow as it uses branching.
C++
int min( int x, int y)
{
return (x < y) ? x : y
}
|
C
int min( int x, int y)
{
return (x < y) ? x : y
}
|
Java
static int min( int x, int y)
{
return (x < y) ? x : y;
}
|
Python3
def min (x, y):
return x if x < y else y
|
C#
static int min( int x, int y)
{
return (x < y) ? x : y;
}
|
Javascript
<script>
function min(x, y)
{
return (x < y) ? x : y;
}
</script>
|
Below are the methods to get minimum(or maximum) without using branching. Typically, the obvious approach is best, though.
Method 1(Use XOR and comparison operator)
Minimum of x and y will be
y ^ ((x ^ y) & -(x < y))
It works because if x < y, then -(x < y) will be -1 which is all ones(11111….), so r = y ^ ((x ^ y) & (111111…)) = y ^ x ^ y = x.
And if x>y, then-(x<y) will be -(0) i.e -(zero) which is zero, so r = y^((x^y) & 0) = y^0 = y.
On some machines, evaluating (x < y) as 0 or 1 requires a branch instruction, so there may be no advantage.
To find the maximum, use
x ^ ((x ^ y) & -(x < y));
C++
#include<iostream>
using namespace std;
class gfg
{
public :
int min( int x, int y)
{
return y ^ ((x ^ y) & -(x < y));
}
int max( int x, int y)
{
return x ^ ((x ^ y) & -(x < y));
}
};
int main()
{
gfg g;
int x = 15;
int y = 6;
cout << "Minimum of " << x <<
" and " << y << " is " ;
cout << g. min(x, y);
cout << "\nMaximum of " << x <<
" and " << y << " is " ;
cout << g.max(x, y);
getchar ();
}
|
C
#include<stdio.h>
int min( int x, int y)
{
return y ^ ((x ^ y) & -(x < y));
}
int max( int x, int y)
{
return x ^ ((x ^ y) & -(x < y));
}
int main()
{
int x = 15;
int y = 6;
printf ( "Minimum of %d and %d is " , x, y);
printf ( "%d" , min(x, y));
printf ( "\nMaximum of %d and %d is " , x, y);
printf ( "%d" , max(x, y));
getchar ();
}
|
Java
public class AWS {
static int min( int x, int y)
{
return y ^ ((x ^ y) & -(x << y));
}
static int max( int x, int y)
{
return x ^ ((x ^ y) & -(x << y));
}
public static void main(String[] args) {
int x = 15 ;
int y = 6 ;
System.out.print( "Minimum of " +x+ " and " +y+ " is " );
System.out.println(min(x, y));
System.out.print( "Maximum of " +x+ " and " +y+ " is " );
System.out.println( max(x, y));
}
}
|
Python3
def min (x, y):
return y ^ ((x ^ y) & - (x < y))
def max (x, y):
return x ^ ((x ^ y) & - (x < y))
x = 15
y = 6
print ( "Minimum of" , x, "and" , y, "is" , end = " " )
print ( min (x, y))
print ( "Maximum of" , x, "and" , y, "is" , end = " " )
print ( max (x, y))
|
C#
using System;
public class AWS
{
public static int min( int x, int y)
{
return y ^ ((x ^ y) & -(x << y));
}
public static int max( int x, int y)
{
return x ^ ((x ^ y) & -(x << y));
}
public static void Main( string [] args)
{
int x = 15;
int y = 6;
Console.Write( "Minimum of " + x + " and " + y + " is " );
Console.WriteLine(min(x, y));
Console.Write( "Maximum of " + x + " and " + y + " is " );
Console.WriteLine(max(x, y));
}
}
|
PHP
<?php
function m_in( $x , $y )
{
return $y ^ (( $x ^ $y ) &
- ( $x < $y ));
}
function m_ax( $x , $y )
{
return $x ^ (( $x ^ $y ) &
- ( $x < $y ));
}
$x = 15;
$y = 6;
echo "Minimum of" , " " , $x , " " , "and" ,
" " , $y , " " , " is " , " " ;
echo m_in( $x , $y );
echo "\nMaximum of" , " " , $x , " " ,
"and" , " " , $y , " " , " is " ;
echo m_ax( $x , $y );
?>
|
Javascript
<script>
function min(x,y)
{
return y ^ ((x ^ y) & -(x << y));
}
function max(x,y)
{
return x ^ ((x ^ y) & -(x << y));
}
let x = 15
let y = 6
document.write( "Minimum of " + x + " and " + y + " is " );
document.write(min(x, y) + "<br>" );
document.write( "Maximum of " + x + " and " + y + " is " );
document.write(max(x, y) + "\n" );
</script>
|
Output:
Minimum of 15 and 6 is 6
Maximum of 15 and 6 is 15
Method 2(Use subtraction and shift)
If we know that
INT_MIN <= (x - y) <= INT_MAX
, then we can use the following, which are faster because (x – y) only needs to be evaluated once.
Minimum of x and y will be
y + ((x - y) & ((x - y) >>(sizeof(int) * CHAR_BIT - 1)))
This method shifts the subtraction of x and y by 31 (if size of integer is 32). If (x-y) is smaller than 0, then (x -y)>>31 will be 1. If (x-y) is greater than or equal to 0, then (x -y)>>31 will be 0.
So if x >= y, we get minimum as y + (x-y)&0 which is y.
If x < y, we get minimum as y + (x-y)&1 which is x.
Similarly, to find the maximum use
x - ((x - y) & ((x - y) >> (sizeof(int) * CHAR_BIT - 1)))
C++
#include <bits/stdc++.h>
using namespace std;
#define CHARBIT 8
int min( int x, int y)
{
return y + ((x - y) & ((x - y) >>
( sizeof ( int ) * CHARBIT - 1)));
}
int max( int x, int y)
{
return x - ((x - y) & ((x - y) >>
( sizeof ( int ) * CHARBIT - 1)));
}
int main()
{
int x = 15;
int y = 6;
cout<< "Minimum of " <<x<< " and " <<y<< " is " ;
cout<<min(x, y);
cout<< "\nMaximum of" <<x<< " and " <<y<< " is " ;
cout<<max(x, y);
}
|
C
#include<stdio.h>
#define CHAR_BIT 8
int min( int x, int y)
{
return y + ((x - y) & ((x - y) >>
( sizeof ( int ) * CHAR_BIT - 1)));
}
int max( int x, int y)
{
return x - ((x - y) & ((x - y) >>
( sizeof ( int ) * CHAR_BIT - 1)));
}
int main()
{
int x = 15;
int y = 6;
printf ( "Minimum of %d and %d is " , x, y);
printf ( "%d" , min(x, y));
printf ( "\nMaximum of %d and %d is " , x, y);
printf ( "%d" , max(x, y));
getchar ();
}
|
Java
class GFG
{
static int CHAR_BIT = 4 ;
static int INT_BIT = 8 ;
static int min( int x, int y)
{
return y + ((x - y) & ((x - y) >>
(INT_BIT * CHAR_BIT - 1 )));
}
static int max( int x, int y)
{
return x - ((x - y) & ((x - y) >>
(INT_BIT * CHAR_BIT - 1 )));
}
public static void main(String[] args)
{
int x = 15 ;
int y = 6 ;
System.out.println( "Minimum of " +x+ " and " +y+ " is " +min(x, y));
System.out.println( "Maximum of " +x+ " and " +y+ " is " +max(x, y));
}
}
|
Python3
import sys;
CHAR_BIT = 8 ;
INT_BIT = sys.getsizeof( int ());
def Min (x, y):
return y + ((x - y) & ((x - y) >>
(INT_BIT * CHAR_BIT - 1 )));
def Max (x, y):
return x - ((x - y) & ((x - y) >>
(INT_BIT * CHAR_BIT - 1 )));
x = 15 ;
y = 6 ;
print ( "Minimum of" , x, "and" ,
y, "is" , Min (x, y));
print ( "Maximum of" , x, "and" ,
y, "is" , Max (x, y));
|
C#
using System;
class GFG
{
static int CHAR_BIT = 8;
static int min( int x, int y)
{
return y + ((x - y) & ((x - y) >>
( sizeof ( int ) * CHAR_BIT - 1)));
}
static int max( int x, int y)
{
return x - ((x - y) & ((x - y) >>
( sizeof ( int ) * CHAR_BIT - 1)));
}
static void Main()
{
int x = 15;
int y = 6;
Console.WriteLine( "Minimum of " +x+ " and " +y+ " is " +min(x, y));
Console.WriteLine( "Maximum of " +x+ " and " +y+ " is " +max(x, y));
}
}
|
Javascript
<script>
var CHAR_BIT = 4;
var INT_BIT = 8;
function min(x , y) {
return y + ((x - y) & ((x - y) >> (INT_BIT * CHAR_BIT - 1)));
}
function max(x , y) {
return x - ((x - y) & ((x - y) >> (INT_BIT * CHAR_BIT - 1)));
}
var x = 15;
var y = 6;
document.write( "Minimum of " + x + " and " + y + " is " + min(x, y)+ "<br/>" );
document.write( "Maximum of " + x + " and " + y + " is " + max(x, y));
</script>
|
Note that the 1989 ANSI C specification doesn’t specify the result of signed right-shift, so above method is not portable. If exceptions are thrown on overflows, then the values of x and y should be unsigned or cast to unsigned for the subtractions to avoid unnecessarily throwing an exception, however the right-shift needs a signed operand to produce all one bits when negative, so cast to signed there.
Method 3 (Use absolute value)
A generalized formula to find the max/min number with absolute value is :
(x + y + ABS(x-y) )/2
Find the min number is:
(x + y - ABS(x-y) )/2
So, if we can use the bitwise operation to find the absolute value, we can find the max/min number without using if conditions. The way to find the absolute way with bitwise operation can be found here:
Step1) Set the mask as right shift of integer by 31 (assuming integers are stored as two’s-complement 32-bit values and that the right-shift operator does sign extension).
mask = n>>31
Step2) XOR the mask with number
mask ^ n
Step3) Subtract mask from result of step 2 and return the result.
(mask^n) - mask
Therefore, we can conclude the solution as follows:
C++
#include <bits/stdc++.h>
using namespace std;
int absbit32( int x, int y)
{
int sub = x - y;
int mask = (sub >> 31);
return (sub ^ mask) - mask;
}
int max( int x, int y)
{
int abs = absbit32(x, y);
return (x + y + abs ) / 2;
}
int min( int x, int y)
{
int abs = absbit32(x, y);
return (x + y - abs ) / 2;
}
int main()
{
cout << max(2, 3) << endl;
cout << max(2, -3) << endl;
cout << max(-2, -3) << endl;
cout << min(2, 3) << endl;
cout << min(2, -3) << endl;
cout << min(-2, -3) << endl;
return 0;
}
|
Java
import java.io.*;
class GFG {
public static void main(String []args){
System.out.println( max( 2 , 3 ) );
System.out.println( max( 2 ,- 3 ) );
System.out.println( max(- 2 ,- 3 ) );
System.out.println( min( 2 , 3 ) );
System.out.println( min( 2 ,- 3 ) );
System.out.println( min(- 2 ,- 3 ) );
}
public static int max( int x, int y){
int abs = absbit32(x,y);
return (x + y + abs)/ 2 ;
}
public static int min( int x, int y){
int abs = absbit32(x,y);
return (x + y - abs)/ 2 ;
}
public static int absbit32( int x, int y){
int sub = x - y;
int mask = (sub >> 31 );
return (sub ^ mask) - mask;
}
}
|
Python3
def max (x, y):
abs = absbit32(x,y)
return (x + y + abs ) / / 2
def min (x, y):
abs = absbit32(x,y)
return (x + y - abs ) / / 2
def absbit32( x, y):
sub = x - y
mask = (sub >> 31 )
return (sub ^ mask) - mask
print ( max ( 2 , 3 ) )
print ( max ( 2 , - 3 ) )
print ( max ( - 2 , - 3 ) )
print ( min ( 2 , 3 ) )
print ( min ( 2 , - 3 ) )
print ( min ( - 2 , - 3 ) )
|
C#
using System;
class GFG{
public static void Main(String []args)
{
Console.WriteLine(max(2, 3));
Console.WriteLine(max(2, -3));
Console.WriteLine(max(-2, -3));
Console.WriteLine(min(2, 3));
Console.WriteLine(min(2, -3));
Console.WriteLine(min(-2, -3));
}
public static int max( int x, int y)
{
int abs = absbit32(x, y);
return (x + y + abs) / 2;
}
public static int min( int x, int y)
{
int abs = absbit32(x, y);
return (x + y - abs) / 2;
}
public static int absbit32( int x, int y)
{
int sub = x - y;
int mask = (sub >> 31);
return (sub ^ mask) - mask;
}
}
|
Javascript
<script>
function max(x , y){
var abs = absbit32(x,y);
return (x + y + abs)/2;
}
function min(x , y){
var abs = absbit32(x,y);
return (x + y - abs)/2;
}
function absbit32(x , y){
var sub = x - y;
var mask = (sub >> 31);
return (sub ^ mask) - mask;
}
document.write( max(2,3)+ "<br>" );
document.write( max(2,-3)+ "<br>" );
document.write( max(-2,-3)+ "<br>" );
document.write( min(2,3)+ "<br>" );
document.write( min(2,-3)+ "<br>" );
document.write( min(-2,-3) );
</script>
|
Source:
http://graphics.stanford.edu/~seander/bithacks.html#IntegerMinOrMax