Pythonでランレングス符号化された文字列をデコードするプログラム
ランレングス符号化とは
ランレングス符号化(Run-Length Encoding、RLE)は、文字列を高速かつシンプルに圧縮できる手法として広く知られています。その基本的な考え方は、「連続して繰り返される文字を、繰り返し回数と文字のペアとして表現する」というものです。
例えば、文字列 "BBBBAAADDCBB" の場合、Bが4回、Aが3回、Dが2回、Cが1回、Bが2回続いているため、"4B3A2D1C2B" とエンコードされます。
本記事では、この逆の処理、すなわちエンコードされた文字列を受け取り、元の文字列へと復元(デコード)するPythonプログラムを解説します。
問題の定義
ランレングス符号化された文字列 s が与えられたとき、そのデコード結果を求めます。
- 入力:
s = "4B3A2D1C2B" - 出力:
"BBBBAAADDCBB"
解法のアプローチ
この問題は、以下の手順で解くことができます。
- デコード結果を格納するための空文字列
outputを用意します。 - 連続する数字を一時的に保持するための空文字列
numを用意します。 - 文字列 s の各文字 i について次の処理を行います。
- i がアルファベットの場合:これまでに読み取った数字(num)を整数に変換し、その回数だけ文字 i を
outputに追加します。その後、numを空にリセットします。 - i が数字の場合:桁が複数ある場合にも対応できるよう、
numに文字を連結して保持します。
- i がアルファベットの場合:これまでに読み取った数字(num)を整数に変換し、その回数だけ文字 i を
- すべての文字を処理し終えたら、
outputを返します。
数字を1桁ずつ文字列として蓄積してから変換している点がポイントです。これにより、「12A」のような2桁以上の繰り返し回数も正しく処理できます。
実装例
それでは、実際のコードを見てみましょう。
class Solution:
def solve(self, s):
output = ""
num = ""
for i in s:
if i.isalpha():
output += i * int(num)
num = ""
else:
num += i
return output
ob = Solution()
print(ob.solve("4B3A2D1C2B"))入力
"4B3A2D1C2B"
出力
BBBBAAADDCBB
処理の流れを追ってみる
入力 "4B3A2D1C2B" の場合、プログラムは次のように動作します。
- 「4」を読み込み、num = "4" となります。
- 「B」を読み込むと、output に B×4 = "BBBB" が追加され、num はリセットされます。
- 同様に「3A」→ "AAA"、「2D」→ "DD"、「1C」→ "C"、「2B」→ "BB" が順に追加されます。
- 最終的に "BBBBAAADDCBB" が出力されます。
計算量について
このアルゴリズムは、入力文字列を一度だけ走査すればよいため、時間計算量は O(n)(n は入力文字列の長さ)です。ただし、Pythonの文字列連結は都度新しい文字列を生成するため、出力が非常に長くなる場合は list に追加して最後に join() で結合すると、より効率的になります。
まとめ
ランレングス符号化された文字列のデコードは、「数字部分を蓄積し、英字が出現した時点で繰り返し展開する」というシンプルなルールで実装できます。圧縮・伸長の基本概念を理解するのに最適な題材なので、ぜひ自分でもコードを書いて動作を確認してみてください。
-
Pythonで行列をZ字形に出力するプログラムの解説
本記事では、n×n の正方行列の要素を「Z」の字形に沿って出力する方法について、その考え方と実装の手順をわかりやすく解説します。 問題の概要 次数 n×n の正方行列が与えられたとき、その要素を Z 字形に従って順番に表示することが求められます。 Z 字形の走査は、以下の3つのステップで構成されます。 まず、最初の行(1行目)を左から右へ走査する 次に、主対角線(左上から右下へ向かう対角成分)を走査する 最後に、最終行(最後の行)を左から右へ走査する ここでは説明のため、あらかじめ用意した入力行列を使用して、コードの流れを示します。 サンプルコード arr = [[1, 2, 6, 9],
-
Pythonで文字のリストを文字列に変換する方法を解説
Pythonでは、リスト内の個々の要素をひとつの文字列にまとめたい場面がよくあります。たとえば、データを保存したり送信したりする際に必要となるシリアライズ(直列化)の処理では、このような変換が非常に役立ちます。具体的には、次のような変換を指します。[h, e, l, l, o, , w, o, r, l, d] → hello worldjoinメソッドを使った変換Pythonには、このような変換を実現するためのjoin()メソッドが標準で用意されています。joinメソッドは、区切り文字(デリミタ)として使う文字列に対して呼び出し、引数に渡したリストの各要素を連結します。今回は各文字をつなげ