Go << and >> operators

GoBitwise Operators

Go Problem Overview


Could someone please explain to me the usage of << and >> in Go? I guess it is similar to some other languages.

Go Solutions


Solution 1 - Go

The super (possibly over) simplified definition is just that << is used for "times 2" and >> is for "divided by 2" - and the number after it is how many times.

So n << x is "n times 2, x times". And y >> z is "y divided by 2, z times".

For example, 1 << 5 is "1 times 2, 5 times" or 32. And 32 >> 5 is "32 divided by 2, 5 times" or 1.

Solution 2 - Go

From the spec at http://golang.org/doc/go_spec.html, it seems that at least with integers, it's a binary shift. for example, binary 0b00001000 >> 1 would be 0b00000100, and 0b00001000 << 1 would be 0b00010000.


Go apparently doesn't accept the 0b notation for binary integers. I was just using it for the example. In decimal, 8 >> 1 is 4, and 8 << 1 is 16. Shifting left by one is the same as multiplication by 2, and shifting right by one is the same as dividing by two, discarding any remainder.

Solution 3 - Go

The << and >> operators are Go Arithmetic Operators.

<<   left shift             integer << unsigned integer
>>   right shift            integer >> unsigned integer

> The shift operators shift the left > operand by the shift count specified > by the right operand. They implement > arithmetic shifts if the left operand > is a signed integer and logical shifts > if it is an unsigned integer. The > shift count must be an unsigned > integer. There is no upper limit on > the shift count. Shifts behave as if > the left operand is shifted n times by > 1 for a shift count of n. As a result, > x << 1 is the same as x*2 and x >> 1 > is the same as x/2 but truncated > towards negative infinity.

Solution 4 - Go

They are basically Arithmetic operators and its the same in other languages here is a basic PHP , C , Go Example

GO

package main

import (
	"fmt"
)

func main() {
	var t , i uint
	t , i = 1 , 1

	for i = 1 ; i < 10 ; i++ {
		fmt.Printf("%d << %d = %d \n", t , i , t<<i)
	}


	fmt.Println()

	t = 512
	for i = 1 ; i < 10 ; i++ {
		fmt.Printf("%d >> %d = %d \n", t , i , t>>i)
	}

}

GO Demo

C

#include <stdio.h>
int main()
{

	int t = 1 ;
	int i = 1 ;
	
	for(i = 1; i < 10; i++) {
		printf("%d << %d = %d \n", t, i, t << i);
	}
	
        printf("\n");
	
	t = 512;
	
	for(i = 1; i < 10; i++) {
		printf("%d >> %d = %d \n", t, i, t >> i);
	}    

  return 0;
}

C Demo

PHP

$t = $i = 1;

for($i = 1; $i < 10; $i++) {
	printf("%d << %d = %d \n", $t, $i, $t << $i);
}

print PHP_EOL;

$t = 512;

for($i = 1; $i < 10; $i++) {
	printf("%d >> %d = %d \n", $t, $i, $t >> $i);
}

PHP Demo

They would all output

1 << 1 = 2 
1 << 2 = 4 
1 << 3 = 8 
1 << 4 = 16 
1 << 5 = 32 
1 << 6 = 64 
1 << 7 = 128 
1 << 8 = 256 
1 << 9 = 512 

512 >> 1 = 256 
512 >> 2 = 128 
512 >> 3 = 64 
512 >> 4 = 32 
512 >> 5 = 16 
512 >> 6 = 8 
512 >> 7 = 4 
512 >> 8 = 2 
512 >> 9 = 1 

Solution 5 - Go

Go's << and >> are similar to shifts (that is: division or multiplication by a power of 2) in other languages, but because Go is a safer language than C/C++ it does some extra work when the shift count is a number.

Shift instructions in x86 CPUs consider only 5 bits (6 bits on 64-bit x86 CPUs) of the shift count. In languages like C/C++, the shift operator translates into a single CPU instruction.

The following Go code

x := 10
y := uint(1025)  // A big shift count
println(x >> y)
println(x << y)

prints

0
0

while a C/C++ program would print

5
20

Solution 6 - Go

<< is left shift. >> is sign-extending right shift when the left operand is a signed integer, and is zero-extending right shift when the left operand is an unsigned integer.

To better understand >> think of

var u uint32 = 0x80000000;
var i int32 = -2;

u >> 1;  // Is 0x40000000 similar to >>> in Java
i >> 1;  // Is -1 similar to >> in Java

So when applied to an unsigned integer, the bits at the left are filled with zero, whereas when applied to a signed integer, the bits at the left are filled with the leftmost bit (which is 1 when the signed integer is negative as per 2's complement).

Solution 7 - Go

In decimal math, when we multiply or divide by 10, we effect the zeros on the end of the number.

In binary, 2 has the same effect. So we are adding a zero to the end, or removing the last digit

Solution 8 - Go

These are Right bitwise and left bitwise operators

Solution 9 - Go

n << x = n * 2^x   Example: 3 << 5 = 3 * 2^5 = 96

y >> z = y / 2^z   Example: 512 >> 4 = 512 / 2^4 = 32

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionbrianohView Question on Stackoverflow
Solution 1 - GoPeter OramView Answer on Stackoverflow
Solution 2 - Gojcomeau_ictxView Answer on Stackoverflow
Solution 3 - GopeterSOView Answer on Stackoverflow
Solution 4 - GoBabaView Answer on Stackoverflow
Solution 5 - Gouser811773View Answer on Stackoverflow
Solution 6 - GoMike SamuelView Answer on Stackoverflow
Solution 7 - Gorobert kingView Answer on Stackoverflow
Solution 8 - Godılo sürücüView Answer on Stackoverflow
Solution 9 - GospatialView Answer on Stackoverflow