Bitwise operations in Python coming from C
I tried rewriting the small C program below in Python, but I am getting different outputs.
C version:
#include <stdio.h>
int main()
{
unsigned char data = 0x00;
unsigned char i;
unsigned char bit = 0x01;
unsigned char parity = 1;
unsigned char value = 0x1c;
for (i = 0; i < 8; i++)
{
data = data | bit;
bit = bit << 1;
parity = parity ^ (data & 0x01);
}
printf("data: %d bit: %d parity: %dn", data, bit, parity);
return 0;
}
Python version:
data = 0
bit = 1
parity = 1
value = int('1c', 16)
for i in range(8):
data = data | bit
bit = bit << 1
parity = parity ^ (data & 1)
print('data: {0} bit: {1} parity: {2}'.format(data, bit, parity))
And the outputs are:
C version
> $ ./test
data: 255 bit: 0 parity: 1
Python version
> $ python3 test.py
data: 255 bit: 256 parity: 1
What am I missing on Python bitwise operations?
python bitwise-operators
add a comment |
I tried rewriting the small C program below in Python, but I am getting different outputs.
C version:
#include <stdio.h>
int main()
{
unsigned char data = 0x00;
unsigned char i;
unsigned char bit = 0x01;
unsigned char parity = 1;
unsigned char value = 0x1c;
for (i = 0; i < 8; i++)
{
data = data | bit;
bit = bit << 1;
parity = parity ^ (data & 0x01);
}
printf("data: %d bit: %d parity: %dn", data, bit, parity);
return 0;
}
Python version:
data = 0
bit = 1
parity = 1
value = int('1c', 16)
for i in range(8):
data = data | bit
bit = bit << 1
parity = parity ^ (data & 1)
print('data: {0} bit: {1} parity: {2}'.format(data, bit, parity))
And the outputs are:
C version
> $ ./test
data: 255 bit: 0 parity: 1
Python version
> $ python3 test.py
data: 255 bit: 256 parity: 1
What am I missing on Python bitwise operations?
python bitwise-operators
You're missing 'ctypes'
– agg3l
Nov 23 '18 at 1:17
2
You are missing that your type is larger than a byte. As such: 128 << 1 = 256 and does not overflow to 0
– planetmaker
Nov 23 '18 at 1:25
@planetmaker, yep; ctypes module is somewhat awkward but consistent way to deal with it. Although not "pythonic" at all )
– agg3l
Nov 23 '18 at 1:44
add a comment |
I tried rewriting the small C program below in Python, but I am getting different outputs.
C version:
#include <stdio.h>
int main()
{
unsigned char data = 0x00;
unsigned char i;
unsigned char bit = 0x01;
unsigned char parity = 1;
unsigned char value = 0x1c;
for (i = 0; i < 8; i++)
{
data = data | bit;
bit = bit << 1;
parity = parity ^ (data & 0x01);
}
printf("data: %d bit: %d parity: %dn", data, bit, parity);
return 0;
}
Python version:
data = 0
bit = 1
parity = 1
value = int('1c', 16)
for i in range(8):
data = data | bit
bit = bit << 1
parity = parity ^ (data & 1)
print('data: {0} bit: {1} parity: {2}'.format(data, bit, parity))
And the outputs are:
C version
> $ ./test
data: 255 bit: 0 parity: 1
Python version
> $ python3 test.py
data: 255 bit: 256 parity: 1
What am I missing on Python bitwise operations?
python bitwise-operators
I tried rewriting the small C program below in Python, but I am getting different outputs.
C version:
#include <stdio.h>
int main()
{
unsigned char data = 0x00;
unsigned char i;
unsigned char bit = 0x01;
unsigned char parity = 1;
unsigned char value = 0x1c;
for (i = 0; i < 8; i++)
{
data = data | bit;
bit = bit << 1;
parity = parity ^ (data & 0x01);
}
printf("data: %d bit: %d parity: %dn", data, bit, parity);
return 0;
}
Python version:
data = 0
bit = 1
parity = 1
value = int('1c', 16)
for i in range(8):
data = data | bit
bit = bit << 1
parity = parity ^ (data & 1)
print('data: {0} bit: {1} parity: {2}'.format(data, bit, parity))
And the outputs are:
C version
> $ ./test
data: 255 bit: 0 parity: 1
Python version
> $ python3 test.py
data: 255 bit: 256 parity: 1
What am I missing on Python bitwise operations?
python bitwise-operators
python bitwise-operators
edited Nov 23 '18 at 3:52
Branson Camp
79111
79111
asked Nov 23 '18 at 1:14
kolriekolrie
6,753105187
6,753105187
You're missing 'ctypes'
– agg3l
Nov 23 '18 at 1:17
2
You are missing that your type is larger than a byte. As such: 128 << 1 = 256 and does not overflow to 0
– planetmaker
Nov 23 '18 at 1:25
@planetmaker, yep; ctypes module is somewhat awkward but consistent way to deal with it. Although not "pythonic" at all )
– agg3l
Nov 23 '18 at 1:44
add a comment |
You're missing 'ctypes'
– agg3l
Nov 23 '18 at 1:17
2
You are missing that your type is larger than a byte. As such: 128 << 1 = 256 and does not overflow to 0
– planetmaker
Nov 23 '18 at 1:25
@planetmaker, yep; ctypes module is somewhat awkward but consistent way to deal with it. Although not "pythonic" at all )
– agg3l
Nov 23 '18 at 1:44
You're missing 'ctypes'
– agg3l
Nov 23 '18 at 1:17
You're missing 'ctypes'
– agg3l
Nov 23 '18 at 1:17
2
2
You are missing that your type is larger than a byte. As such: 128 << 1 = 256 and does not overflow to 0
– planetmaker
Nov 23 '18 at 1:25
You are missing that your type is larger than a byte. As such: 128 << 1 = 256 and does not overflow to 0
– planetmaker
Nov 23 '18 at 1:25
@planetmaker, yep; ctypes module is somewhat awkward but consistent way to deal with it. Although not "pythonic" at all )
– agg3l
Nov 23 '18 at 1:44
@planetmaker, yep; ctypes module is somewhat awkward but consistent way to deal with it. Although not "pythonic" at all )
– agg3l
Nov 23 '18 at 1:44
add a comment |
1 Answer
1
active
oldest
votes
As you can see, the only difference in the output is the value of the variable bit
.
In your C program, the variable bit
is declared as unsigned char
. That means it takes on only the values 0
through 255
. The last operation on bit
in your code is
bit = bit << 1
Before the last time that line is executed, bit
is 128
. After that line, it "tries" to become 256
but that does not fit into an unsigned char
. So overflow happens, not flagged by your program, and bit
becomes 0
.
In the Python program, the variable bit
is simply an integer, int
, which has no maximum size. So there is no overflow, and bit
does become 256
.
There are several ways to overcome that difference in Python. You could force bit
to stay in the desired range by instead using
bit = (bit << 1) % 256
or perhaps
bit = (bit << 1) & 255
You could instead make bit
to be the equivalent of an unsigned char
variable. As a comment says, you could use the ctypes
module, I believe. You could also use numpy
(I'm more familiar with that).
1
damn beat me to it (just barely). have an upvote.
– CoffeeTableEspresso
Nov 23 '18 at 1:27
Exactly, Python is not aware about "small" integer types…
– agg3l
Nov 23 '18 at 1:43
@RoryDaulton Maybe you should rephrase it, considering google will match this some day: "In the Python program, bit is just an integer."
– agg3l
Nov 23 '18 at 1:47
@agg3l: I rephrased it. Is that what you meant?
– Rory Daulton
Nov 23 '18 at 1:48
@RoryDaulton Confusing naming of variables in Python code sample (assuming byte-aware integer types, which are not really there) by kolrie has already and may lead to more confusion later. As long as Python is not low-level language by design. That was my idea
– agg3l
Nov 23 '18 at 1:55
|
show 1 more comment
Your Answer
StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");
StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "1"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);
StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});
function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});
}
});
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53439614%2fbitwise-operations-in-python-coming-from-c%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
1 Answer
1
active
oldest
votes
1 Answer
1
active
oldest
votes
active
oldest
votes
active
oldest
votes
As you can see, the only difference in the output is the value of the variable bit
.
In your C program, the variable bit
is declared as unsigned char
. That means it takes on only the values 0
through 255
. The last operation on bit
in your code is
bit = bit << 1
Before the last time that line is executed, bit
is 128
. After that line, it "tries" to become 256
but that does not fit into an unsigned char
. So overflow happens, not flagged by your program, and bit
becomes 0
.
In the Python program, the variable bit
is simply an integer, int
, which has no maximum size. So there is no overflow, and bit
does become 256
.
There are several ways to overcome that difference in Python. You could force bit
to stay in the desired range by instead using
bit = (bit << 1) % 256
or perhaps
bit = (bit << 1) & 255
You could instead make bit
to be the equivalent of an unsigned char
variable. As a comment says, you could use the ctypes
module, I believe. You could also use numpy
(I'm more familiar with that).
1
damn beat me to it (just barely). have an upvote.
– CoffeeTableEspresso
Nov 23 '18 at 1:27
Exactly, Python is not aware about "small" integer types…
– agg3l
Nov 23 '18 at 1:43
@RoryDaulton Maybe you should rephrase it, considering google will match this some day: "In the Python program, bit is just an integer."
– agg3l
Nov 23 '18 at 1:47
@agg3l: I rephrased it. Is that what you meant?
– Rory Daulton
Nov 23 '18 at 1:48
@RoryDaulton Confusing naming of variables in Python code sample (assuming byte-aware integer types, which are not really there) by kolrie has already and may lead to more confusion later. As long as Python is not low-level language by design. That was my idea
– agg3l
Nov 23 '18 at 1:55
|
show 1 more comment
As you can see, the only difference in the output is the value of the variable bit
.
In your C program, the variable bit
is declared as unsigned char
. That means it takes on only the values 0
through 255
. The last operation on bit
in your code is
bit = bit << 1
Before the last time that line is executed, bit
is 128
. After that line, it "tries" to become 256
but that does not fit into an unsigned char
. So overflow happens, not flagged by your program, and bit
becomes 0
.
In the Python program, the variable bit
is simply an integer, int
, which has no maximum size. So there is no overflow, and bit
does become 256
.
There are several ways to overcome that difference in Python. You could force bit
to stay in the desired range by instead using
bit = (bit << 1) % 256
or perhaps
bit = (bit << 1) & 255
You could instead make bit
to be the equivalent of an unsigned char
variable. As a comment says, you could use the ctypes
module, I believe. You could also use numpy
(I'm more familiar with that).
1
damn beat me to it (just barely). have an upvote.
– CoffeeTableEspresso
Nov 23 '18 at 1:27
Exactly, Python is not aware about "small" integer types…
– agg3l
Nov 23 '18 at 1:43
@RoryDaulton Maybe you should rephrase it, considering google will match this some day: "In the Python program, bit is just an integer."
– agg3l
Nov 23 '18 at 1:47
@agg3l: I rephrased it. Is that what you meant?
– Rory Daulton
Nov 23 '18 at 1:48
@RoryDaulton Confusing naming of variables in Python code sample (assuming byte-aware integer types, which are not really there) by kolrie has already and may lead to more confusion later. As long as Python is not low-level language by design. That was my idea
– agg3l
Nov 23 '18 at 1:55
|
show 1 more comment
As you can see, the only difference in the output is the value of the variable bit
.
In your C program, the variable bit
is declared as unsigned char
. That means it takes on only the values 0
through 255
. The last operation on bit
in your code is
bit = bit << 1
Before the last time that line is executed, bit
is 128
. After that line, it "tries" to become 256
but that does not fit into an unsigned char
. So overflow happens, not flagged by your program, and bit
becomes 0
.
In the Python program, the variable bit
is simply an integer, int
, which has no maximum size. So there is no overflow, and bit
does become 256
.
There are several ways to overcome that difference in Python. You could force bit
to stay in the desired range by instead using
bit = (bit << 1) % 256
or perhaps
bit = (bit << 1) & 255
You could instead make bit
to be the equivalent of an unsigned char
variable. As a comment says, you could use the ctypes
module, I believe. You could also use numpy
(I'm more familiar with that).
As you can see, the only difference in the output is the value of the variable bit
.
In your C program, the variable bit
is declared as unsigned char
. That means it takes on only the values 0
through 255
. The last operation on bit
in your code is
bit = bit << 1
Before the last time that line is executed, bit
is 128
. After that line, it "tries" to become 256
but that does not fit into an unsigned char
. So overflow happens, not flagged by your program, and bit
becomes 0
.
In the Python program, the variable bit
is simply an integer, int
, which has no maximum size. So there is no overflow, and bit
does become 256
.
There are several ways to overcome that difference in Python. You could force bit
to stay in the desired range by instead using
bit = (bit << 1) % 256
or perhaps
bit = (bit << 1) & 255
You could instead make bit
to be the equivalent of an unsigned char
variable. As a comment says, you could use the ctypes
module, I believe. You could also use numpy
(I'm more familiar with that).
edited Nov 23 '18 at 11:47
answered Nov 23 '18 at 1:26
Rory DaultonRory Daulton
14k41933
14k41933
1
damn beat me to it (just barely). have an upvote.
– CoffeeTableEspresso
Nov 23 '18 at 1:27
Exactly, Python is not aware about "small" integer types…
– agg3l
Nov 23 '18 at 1:43
@RoryDaulton Maybe you should rephrase it, considering google will match this some day: "In the Python program, bit is just an integer."
– agg3l
Nov 23 '18 at 1:47
@agg3l: I rephrased it. Is that what you meant?
– Rory Daulton
Nov 23 '18 at 1:48
@RoryDaulton Confusing naming of variables in Python code sample (assuming byte-aware integer types, which are not really there) by kolrie has already and may lead to more confusion later. As long as Python is not low-level language by design. That was my idea
– agg3l
Nov 23 '18 at 1:55
|
show 1 more comment
1
damn beat me to it (just barely). have an upvote.
– CoffeeTableEspresso
Nov 23 '18 at 1:27
Exactly, Python is not aware about "small" integer types…
– agg3l
Nov 23 '18 at 1:43
@RoryDaulton Maybe you should rephrase it, considering google will match this some day: "In the Python program, bit is just an integer."
– agg3l
Nov 23 '18 at 1:47
@agg3l: I rephrased it. Is that what you meant?
– Rory Daulton
Nov 23 '18 at 1:48
@RoryDaulton Confusing naming of variables in Python code sample (assuming byte-aware integer types, which are not really there) by kolrie has already and may lead to more confusion later. As long as Python is not low-level language by design. That was my idea
– agg3l
Nov 23 '18 at 1:55
1
1
damn beat me to it (just barely). have an upvote.
– CoffeeTableEspresso
Nov 23 '18 at 1:27
damn beat me to it (just barely). have an upvote.
– CoffeeTableEspresso
Nov 23 '18 at 1:27
Exactly, Python is not aware about "small" integer types…
– agg3l
Nov 23 '18 at 1:43
Exactly, Python is not aware about "small" integer types…
– agg3l
Nov 23 '18 at 1:43
@RoryDaulton Maybe you should rephrase it, considering google will match this some day: "In the Python program, bit is just an integer."
– agg3l
Nov 23 '18 at 1:47
@RoryDaulton Maybe you should rephrase it, considering google will match this some day: "In the Python program, bit is just an integer."
– agg3l
Nov 23 '18 at 1:47
@agg3l: I rephrased it. Is that what you meant?
– Rory Daulton
Nov 23 '18 at 1:48
@agg3l: I rephrased it. Is that what you meant?
– Rory Daulton
Nov 23 '18 at 1:48
@RoryDaulton Confusing naming of variables in Python code sample (assuming byte-aware integer types, which are not really there) by kolrie has already and may lead to more confusion later. As long as Python is not low-level language by design. That was my idea
– agg3l
Nov 23 '18 at 1:55
@RoryDaulton Confusing naming of variables in Python code sample (assuming byte-aware integer types, which are not really there) by kolrie has already and may lead to more confusion later. As long as Python is not low-level language by design. That was my idea
– agg3l
Nov 23 '18 at 1:55
|
show 1 more comment
Thanks for contributing an answer to Stack Overflow!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53439614%2fbitwise-operations-in-python-coming-from-c%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
You're missing 'ctypes'
– agg3l
Nov 23 '18 at 1:17
2
You are missing that your type is larger than a byte. As such: 128 << 1 = 256 and does not overflow to 0
– planetmaker
Nov 23 '18 at 1:25
@planetmaker, yep; ctypes module is somewhat awkward but consistent way to deal with it. Although not "pythonic" at all )
– agg3l
Nov 23 '18 at 1:44