Pythonでプログラミングをしていると、10進数と2進数の間で数値を変換する必要が出てくることがあります。ビット演算を行う場合や、低レベルなデータ処理、ネットワークプログラミングなどでは、2進数での表現が重要になってくるでしょう。
しかし、「どの関数を使えばいいのか」「変換結果の形式はどうなるのか」「エラーが出たときの対処法は」など、初心者の方にとっては疑問点も多いのではないでしょうか。
この記事では、Pythonにおける10進数と2進数の変換方法について、bin()関数とint()関数を中心に、基本的な使い方から実践的な応用例まで詳しく解説していきます。コード例を豊富に掲載していますので、実際に手を動かしながら理解を深めていただけます。
Pythonでの10進数と2進数変換の基本
それではまず、Pythonにおける10進数と2進数の変換方法の基本について解説していきます。
bin()関数による10進数から2進数への変換
Pythonで10進数を2進数に変換するには、
。この関数は非常にシンプルで、10進数の整数を引数として渡すだけで、2進数表記の文字列を返してくれるのです。
基本的な使い方を見てみましょう。
# 10進数の10を2進数に変換
result = bin(10)
print(result) # 出力: 0b1010
bin()関数は、戻り値として「0b」というプレフィックスが付いた文字列を返します。この「0b」は、その後に続く数字が2進数であることを示す接頭辞です。
正の数だけでなく、負の数や0も変換可能です。負の数の場合は、マイナス記号が先頭に付加されます。
print(bin(0)) # 出力: 0b0
print(bin(255)) # 出力: 0b11111111
print(bin(-10)) # 出力: -0b1010
int()関数による2進数から10進数への変換
逆に、2進数から10進数への変換にはint()関数を使用します。int()関数は第1引数に変換したい文字列、第2引数に基数(何進数か)を指定することで、様々な進数から10進数への変換が可能です。
2進数から10進数への変換では、第2引数に2を指定するのです。
# 2進数の文字列を10進数に変換
result = int('1010', 2)
print(result) # 出力: 10
# 0bプレフィックス付きでも変換可能
result2 = int('0b1010', 2)
print(result2) # 出力: 10
int()関数は、「0b」プレフィックスの有無に関わらず正しく変換してくれます。これにより、bin()関数の出力をそのままint()関数に渡すことも可能でしょう。
変換結果の特徴と注意点
10進数と2進数の変換を行う際には、いくつか押さえておくべき特徴と注意点があります。
まず、bin()関数の戻り値は文字列型(str)である点に注意が必要です。数値として計算に使用する場合は、再度int()で変換する必要があります。
| 関数 | 入力 | 出力 | 出力の型 |
|---|---|---|---|
| bin() | 整数(int) | ‘0b…’形式の文字列 | str |
| int(x, 2) | 2進数文字列(str) | 10進数の整数 | int |
また、bin()関数は整数のみを受け付けます。浮動小数点数を渡すとエラーになるため、事前にint()で整数化するか、別の方法を検討する必要があるでしょう。
# これはエラーになります
# result = bin(10.5) # TypeError: 'float' object cannot be interpreted as an integer
# 整数化してから変換
result = bin(int(10.5))
print(result) # 出力: 0b1010
10進数から2進数への変換方法の詳細
続いては、10進数から2進数への変換について、より詳しく確認していきます。
bin()関数の基本的な使い方
bin()関数は、Pythonの組み込み関数の中でも特にシンプルな使い方ができます。引数は1つだけで、変換したい整数を渡すだけです。
実際の使用例をいくつか見てみましょう。
# 基本的な変換
num = 42
binary = bin(num)
print(f"{num}の2進数表現: {binary}") # 出力: 42の2進数表現: 0b101010
# ループで複数の数値を変換
for i in range(1, 6):
print(f"{i} → {bin(i)}")
# 出力:
# 1 → 0b1
# 2 → 0b10
# 3 → 0b11
# 4 → 0b100
# 5 → 0b101
bin()関数は非常に高速で、大きな数値でも瞬時に変換が完了します。処理速度を気にする必要はほとんどないでしょう。
また、bin()関数は負の数にも対応しています。負の数の場合は、先頭にマイナス記号が付き、その後に「0b」プレフィックスと2進数表現が続きます。
positive = 10
negative = -10
print(bin(positive)) # 出力: 0b1010
print(bin(negative)) # 出力: -0b1010
format()関数を使った変換方法
bin()関数以外にも、format()関数やf文字列を使って2進数に変換することができます。この方法は、出力形式をより柔軟にカスタマイズしたい場合に便利です。
format()関数では、フォーマット指定子として’b’を使用します。
num = 10
# format()関数を使用
binary1 = format(num, 'b')
print(binary1) # 出力: 1010 (0bプレフィックスなし)
# f文字列を使用
binary2 = f"{num:b}"
print(binary2) # 出力: 1010
# ゼロ埋めを指定(8桁)
binary3 = format(num, '08b')
print(binary3) # 出力: 00001010
format()関数の利点は、
です。特に、固定長の2進数表現が必要な場合に重宝するでしょう。
| フォーマット | 説明 | 例(10の場合) |
|---|---|---|
| :b | 2進数表記 | 1010 |
| :08b | 8桁ゼロ埋め2進数 | 00001010 |
| :#b | 0bプレフィックス付き | 0b1010 |
0bプレフィックスを除去する方法
bin()関数で変換した結果から「0b」プレフィックスを除去したい場合があります。これにはいくつかの方法があるのです。
最もシンプルな方法は、文字列のスライス機能を使って最初の2文字を除去することでしょう。
num = 42
# bin()で変換
binary_with_prefix = bin(num)
print(binary_with_prefix) # 出力: 0b101010
# スライスで0bを除去
binary_without_prefix = binary_with_prefix[2:]
print(binary_without_prefix) # 出力: 101010
# replace()メソッドを使う方法
binary_replaced = binary_with_prefix.replace('0b', '')
print(binary_replaced) # 出力: 101010
# format()を使えば最初からプレフィックスなし
binary_format = format(num, 'b')
print(binary_format) # 出力: 101010
ただし、負の数の場合はスライスの位置に注意が必要です。マイナス記号を保持しながらプレフィックスだけを除去するには、工夫が必要でしょう。
negative = -10
binary = bin(negative) # -0b1010
# replace()を使うのが安全
result = binary.replace('0b', '')
print(result) # 出力: -1010
# または条件分岐
if binary.startswith('-'):
result = '-' + binary[3:]
else:
result = binary[2:]
print(result) # 出力: -1010
2進数から10進数への変換方法の詳細
続いては、2進数から10進数への変換について詳しく見ていきます。
int()関数の基本的な使い方
int()関数で2進数を10進数に変換する際は、
します。この基数指定により、文字列が何進数で表現されているかをPythonに伝えるのです。
基本的な使用例を確認しましょう。
# 2進数文字列を10進数に変換
binary1 = '1010'
decimal1 = int(binary1, 2)
print(decimal1) # 出力: 10
# 0bプレフィックス付きでもOK
binary2 = '0b1010'
decimal2 = int(binary2, 2)
print(decimal2) # 出力: 10
# より大きな数値
binary3 = '11111111'
decimal3 = int(binary3, 2)
print(decimal3) # 出力: 255
int()関数は、文字列に含まれる空白を無視してくれます。ただし、0と1以外の数字が含まれているとエラーになります。
# 空白があってもOK
result1 = int(' 1010 ', 2)
print(result1) # 出力: 10
# アンダースコア区切り(Python 3.6以降)
result2 = int('1111_0000', 2)
print(result2) # 出力: 240
# 負の数
result3 = int('-1010', 2)
print(result3) # 出力: -10
文字列形式の2進数を変換する
実際のプログラムでは、ファイルから読み込んだデータや、ユーザー入力として受け取った文字列を変換する必要があることが多いでしょう。そのような場合の処理方法を見ていきます。
# ユーザー入力を想定
user_input = "1010"
decimal = int(user_input, 2)
print(f"入力された2進数{user_input}は、10進数で{decimal}です")
# リストに格納された2進数文字列を一括変換
binary_list = ['101', '110', '111', '1000']
decimal_list = [int(b, 2) for b in binary_list]
print(decimal_list) # 出力: [5, 6, 7, 8]
# 辞書に変換結果を格納
binary_data = {
'data1': '1010',
'data2': '1100',
'data3': '1111'
}
decimal_data = {key: int(value, 2) for key, value in binary_data.items()}
print(decimal_data) # 出力: {'data1': 10, 'data2': 12, 'data3': 15}
また、bin()関数の出力をそのまま変換することもできます。この場合、0bプレフィックスの有無を気にする必要がないのが便利な点です。
# bin()で変換した結果を再度10進数に戻す
original = 42
binary = bin(original)
print(f"2進数: {binary}") # 出力: 2進数: 0b101010
# そのまま変換可能
restored = int(binary, 2)
print(f"復元: {restored}") # 出力: 復元: 42
# 確認
print(original == restored) # 出力: True
エラー処理と例外対応
2進数から10進数への変換では、不正な文字列が渡されるとValueErrorが発生します。実用的なプログラムでは、適切なエラー処理を実装することが重要でしょう。
def safe_binary_to_decimal(binary_str):
"""
安全に2進数を10進数に変換する関数
"""
try:
# 前後の空白を除去
binary_str = binary_str.strip()
# 変換実行
result = int(binary_str, 2)
return result
except ValueError as e:
print(f"エラー: '{binary_str}'は有効な2進数ではありません")
return None
# 使用例
print(safe_binary_to_decimal('1010')) # 出力: 10
print(safe_binary_to_decimal('0b1100')) # 出力: 12
print(safe_binary_to_decimal('1012')) # エラーメッセージ表示、None返却
print(safe_binary_to_decimal('abc')) # エラーメッセージ表示、None返却
より詳細なバリデーションを行う場合は、正規表現を使って事前チェックすることもできます。
import re
def validate_and_convert(binary_str):
"""
2進数文字列をバリデーションして変換
"""
# 2進数パターン(0bプレフィックス、負の数にも対応)
pattern = r'^-?0?b?[01]+$'
if re.match(pattern, binary_str.strip()):
return int(binary_str, 2)
else:
raise ValueError(f"'{binary_str}'は有効な2進数形式ではありません")
# 使用例
try:
print(validate_and_convert('1010')) # 出力: 10
print(validate_and_convert('-0b1100')) # 出力: -12
print(validate_and_convert('1012')) # ValueError発生
except ValueError as e:
print(e)
実践的な応用例とコード集
続いては、実際のプログラミングで役立つ応用例を確認していきます。
複数の数値を一括変換する
実務では、複数の数値をまとめて変換する必要があることが多いでしょう。リスト内包表記やmap関数を使うと、効率的に処理できます。
# 10進数のリストを2進数に一括変換
decimal_numbers = [1, 2, 3, 4, 5, 10, 15, 20]
# リスト内包表記を使用
binary_list1 = [bin(n) for n in decimal_numbers]
print(binary_list1)
# 出力: ['0b1', '0b10', '0b11', '0b100', '0b101', '0b1010', '0b1111', '0b10100']
# 0bプレフィックスなしで取得
binary_list2 = [format(n, 'b') for n in decimal_numbers]
print(binary_list2)
# 出力: ['1', '10', '11', '100', '101', '1010', '1111', '10100']
# 8桁ゼロ埋めで統一
binary_list3 = [format(n, '08b') for n in decimal_numbers]
print(binary_list3)
# 出力: ['00000001', '00000010', '00000011', '00000100', '00000101',
# '00001010', '00001111', '00010100']
逆に、2進数のリストを10進数に変換する場合も同様です。
# 2進数のリストを10進数に変換
binary_strings = ['1010', '1100', '1111', '10000']
# リスト内包表記
decimal_list = [int(b, 2) for b in binary_strings]
print(decimal_list) # 出力: [10, 12, 15, 16]
# map関数を使用
decimal_list2 = list(map(lambda x: int(x, 2), binary_strings))
print(decimal_list2) # 出力: [10, 12, 15, 16]
# 辞書形式で対応表を作成
conversion_table = {b: int(b, 2) for b in binary_strings}
print(conversion_table)
# 出力: {'1010': 10, '1100': 12, '1111': 15, '10000': 16}
ビット演算との組み合わせ
2進数変換は、ビット演算の結果を視覚的に確認する際に非常に便利です。ビットマスクやビットシフト操作と組み合わせた例を見てみましょう。
# ビット演算の結果を2進数で確認
a = 12 # 0b1100
b = 10 # 0b1010
print(f"a = {a:4d} ({bin(a)})")
print(f"b = {b:4d} ({bin(b)})")
print()
# AND演算
result_and = a & b
print(f"a & b = {result_and:4d} ({format(result_and, '08b')})")
# OR演算
result_or = a | b
print(f"a | b = {result_or:4d} ({format(result_or, '08b')})")
# XOR演算
result_xor = a ^ b
print(f"a ^ b = {result_xor:4d} ({format(result_xor, '08b')})")
# ビットシフト
left_shift = a << 2
print(f"a << 2 = {left_shift:4d} ({format(left_shift, '08b')})") right_shift = a >> 2
print(f"a >> 2 = {right_shift:4d} ({format(right_shift, '08b')})")
また、特定のビットが立っているかを確認する処理もよく使われます。
# 権限管理などで使用されるビットフラグ
READ = 0b001 # 1
WRITE = 0b010 # 2
EXECUTE = 0b100 # 4
# ユーザーの権限(読み取りと実行が可能)
user_permission = READ | EXECUTE # 0b101 = 5
print(f"ユーザー権限: {bin(user_permission)}")
# 特定の権限を持っているか確認
has_read = bool(user_permission & READ)
has_write = bool(user_permission & WRITE)
has_execute = bool(user_permission & EXECUTE)
print(f"読み取り権限: {has_read}") # True
print(f"書き込み権限: {has_write}") # False
print(f"実行権限: {has_execute}") # True
負の数の2進数表現
Pythonでの負の数の2進数表現は、単純にマイナス記号を付けた形式になります。しかし、コンピュータ内部では2の補数表現が使われているため、実際のビットパターンを確認したい場合は工夫が必要です。
# 正の数と負の数
positive = 10
negative = -10
print(f"正の数: {bin(positive)}") # 出力: 0b1010
print(f"負の数: {bin(negative)}") # 出力: -0b1010
# 2の補数表現を得る(32ビット符号付き整数として)
def to_twos_complement(num, bits=32):
"""2の補数表現を取得"""
if num >= 0:
return format(num, f'0{bits}b')
else:
# 2の補数を計算
return format((1 << bits) + num, f'0{bits}b')
# 使用例
print(f"\n8ビットでの表現:")
print(f" 10: {to_twos_complement(10, 8)}")
print(f"-10: {to_twos_complement(-10, 8)}")
print(f"\n16ビットでの表現:")
print(f" 10: {to_twos_complement(10, 16)}")
print(f"-10: {to_twos_complement(-10, 16)}")
また、特定のビット幅に収まる範囲での変換も実装できます。
def int_to_binary(num, bits=8):
"""
整数を指定ビット幅の2進数文字列に変換
範囲外の場合は例外を発生
"""
max_val = (1 << (bits - 1)) - 1 # 符号付き最大値
min_val = -(1 << (bits - 1)) # 符号付き最小値
if num < min_val or num > max_val:
raise ValueError(f"{bits}ビットの範囲({min_val}~{max_val})を超えています")
if num >= 0:
return format(num, f'0{bits}b')
else:
return format((1 << bits) + num, f'0{bits}b')
# 使用例
print(int_to_binary(10, 8)) # 出力: 00001010
print(int_to_binary(-10, 8)) # 出力: 11110110
print(int_to_binary(127, 8)) # 出力: 01111111
print(int_to_binary(-128, 8)) # 出力: 10000000
まとめ
Pythonでの10進数と2進数の変換は、bin()関数とint()関数を使うことで簡単に実現できます。10進数から2進数への変換にはbin()を、2進数から10進数への変換にはint(x, 2)を使用するのが基本です。
bin()関数は「0b」プレフィックス付きの文字列を返すため、必要に応じてスライスやreplace()で除去できます。また、format()関数やf文字列を使えば、プレフィックスなしの出力やゼロ埋めなど、柔軟な形式で変換が可能でしょう。
int()関数は、0bプレフィックスの有無に関わらず変換でき、負の数やアンダースコア区切りの文字列にも対応しています。実用的なプログラムでは、try-except文を使った適切なエラー処理を実装することが重要です。
ビット演算との組み合わせや、複数の数値の一括変換、2の補数表現の取得など、実践的な応用例も豊富にあります。これらのテクニックを身につけることで、低レベルなデータ処理やネットワークプログラミングなど、様々な場面で活用できるのです。
2進数と10進数の変換をマスターすることで、Pythonでのプログラミングの幅が大きく広がります。ぜひ実際にコードを動かしながら、理解を深めていきましょう。