-
Python(Matplotlib)でグラフに凡例を追加する方法を徹底解説
はじめにグラフの最大の目的は、データをわかりやすく伝えることです。「百聞は一見に如かず」という言葉のとおり、言葉では表現しにくい複雑な情報も、一枚の図やグラフがあれば直感的に伝えることができます。しかし、多くの情報を含むグラフを描く場合は、どのデータがどの要素に対応しているのかを読み手が理解できるよう、凡例(legend)を添えると効果的です。準備:matplotlibのインストールとデータ作成matplotlibでは、凡例をさまざまな方法で表示できます。また、特定のポイントに注目させたい場合には注釈(annotation)も有効で、グラフ上の情報を読み手が理解する助けになります。まず、Pyt
-
PythonでWord文書の段落を作成し、画像を挿入する方法
はじめに データエンジニアリングのスペシャリストとして、テスターからMicrosoft Word形式のテスト結果を受け取ることがよくあります。ため息が出るほど…スクリーンショットや非常に長い段落など、大量の情報をWord文書に詰め込んでくるのです。 先日、テストチームから「ツールが生成したテキストと画像(自動スクリーンショットで取得したもの。本記事では扱いません)を文書に挿入するプログラム」の作成を依頼されました。 MS Wordは他のドキュメント形式と異なり、ページという概念を持たず、残念ながら段落ベースで動作します。そのため、改行(ブレーク)やセクションを活用して、文書を適切に分割する必
-
PythonでMicrosoft Word文書を読み取る方法 ― zipfileでdocxのXMLを抽出する
はじめに 失礼を承知で言うと、筆者はMicrosoft Wordも表計算ソフトもそれほど好きではありません。データエンジニアリングの専門家として、テスターの方々からテスト結果をMicrosoft Word形式で受け取ることがよくあります。ため息が出るのも無理はありません。スクリーンショット、リンク、そして長い・非常に長い・極端に長い段落まで、膨大な情報がWordドキュメントに詰め込まれているのです。Microsoft Wordには、本来シンプルなテキストで済むはずの情報を、開くのに時間がかかり、環境によっては書式が崩れてしまうような扱いにくい巨大ファイルへと変えてしまう「特別な才能」があります
-
Pythonで構造化された文字列から必要なデータを抽出する方法を徹底解説
はじめに本記事では、構造化された文字列(ログなど)から必要なデータやフィールドを抽出するための複数の方法を紹介します。これらのアプローチは、入力データのフォーマットがあらかじめ分かっている場合に特に有効です。想定するデータ形式まずは、アプローチを理解するためにサンプルのフォーマットを作成しましょう。Report: <> - Time: <> - Player: <> - Titles: - Country: <>実際のデータは以下のようなイメージです。report = Report: Daily_Report - Time: 2020-10-10
-
Python Matplotlibでカスタムカラーとカスタム領域サイズを使って4D散布図をプロットする方法
はじめに散布図(Scatter Plot)は、2つの変数間に関係性があるかどうかを確認するために、2次元データを視覚化する際に非常に便利なグラフです。散布図では、データがX値とY値を持つ点(ドット)として表現されます。実装手順1. matplotlibのインストールまず、以下のコマンドでmatplotlibをインストールします。pip install matplotlib2. matplotlibのインポートimport matplotlib.pyplot as plttennis_stats = ((Federer, 20),(Nadal, 20),(Djokovic, 17),(Sampr
-
Python Matplotlibで円グラフの一部を強調表示して描画する方法
はじめに あなたが最も好きなグラフの種類は何ですか?経営層やビジネスアナリストにこの質問をすると、即座に「円グラフ(パイチャート)!」と答えられるほど、円グラフは割合を視覚的に表現するための最も一般的な手法のひとつです。 この記事では、PythonのMatplotlibを使って基本的な円グラフを描く方法から、explodeパラメータで特定のセクターを強調表示するテクニック、さらにパーセンテージではなく実際の値をラベルとして表示するカスタム関数の実装まで、段階的に解説します。 基本的な円グラフの作成手順 ステップ1:Matplotlibのインストール まず、以下のコマンドでMatplotlibを
-
Pythonのargparseでnargsを使って同じ型の位置引数を複数指定する方法
はじめに2つの数値に対して四則演算を行うプログラムを書く場合、それぞれを個別の位置引数(positional argument)として定義することができます。しかし、両方の引数が同じ種類・同じPythonデータ型であるなら、argparseの nargs オプションを使って「同じ型の値をちょうど2つ受け取る」と指定する方が、よりシンプルで自然な設計になります。実装方法ここでは、2つの整数を受け取って減算を行うプログラムを作成してみましょう。両方の引数は同じ int 型です。サンプルコードimport argparse def get_args(): Function : get_a
-
Pythonのargparseでchoicesオプションを使ってコマンドライン引数の値を制限する方法
はじめにここでは、ユーザーからテニスのグランドスラム優勝回数を受け付けて処理するプログラムを例に考えてみましょう。2020年時点では、フェデラーとナダルが最多となる20回のグランドスラムタイトルを保持しており、一方、まだ1度も優勝できていない選手も数多く存在します。つまり、有効な値は0〜20回の範囲内ということになります。まずは、優勝回数を受け付ける基本的なプログラムを作成してみます。注意: プログラムはターミナルから実行してください。サンプルコードimport argparse def get_args(): Function : get_args parameters
-
【Python】数値リストから長さ3以上の等差数列を数えるプログラム
数値のリスト nums が与えられたとき、その中に含まれる「長さ3以上の連続する等差数列」の個数を求める問題を考えます。等差数列とは、隣り合う数同士の差(公差)がすべて等しい数列のことです。 例えば、入力が nums = [6, 8, 10, 12, 13, 14] の場合、出力は 4 になります。次の4つの等差数列が見つかるためです。 [6, 8, 10] [8, 10, 12] [6, 8, 10, 12] [12, 13, 14] 解法のアプローチ この問題は、リストを一度走査するだけで解くことができます。基本的なアイデアは、「同じ差が何回連続して現れたか」をカウントし、そのカウント
-
Pythonで数値リストから等差部分列の個数を求めるプログラム
数値のリスト nums が与えられたとき、長さ3以上の等差部分列(算術サブシーケンス)の個数を求める問題を考えてみましょう。等差数列とは、隣り合う数同士の差がすべて等しい数列のことです。例えば、入力が nums = [6, 12, 13, 8, 10, 14] の場合、出力は 3 になります。これは、[6, 8, 10]、[6, 10, 14]、[12, 13, 14] という3つの等差部分列が存在するためです。解法のアプローチ:動的計画法(DP)この問題は、動的計画法を使って効率的に解くことができます。各インデックスと公差(差分)の組み合わせごとに、そこで終わる等差部分列の個数を記録していく
-
Pythonで+と−を配置して合計をターゲット値に一致させる方法の数を求めるプログラム
問題の概要 負でない整数のリスト nums と整数 target が与えられます。それぞれの要素に対して「+」または「-」の記号を割り当て、式全体の評価結果が target と一致するような配置が何通りあるかを求めます。 たとえば、入力が nums = [2, 3, 3, 3, 2]、target = 9 の場合、出力は 2 になります。条件を満たすのは次の2通りです。 -2 + 3 + 3 + 3 + 2 2 + 3 + 3 + 3 - 2 考え方:部分和問題への置き換え この問題は、動的計画法(DP)による「部分集合の数え上げ」として定式化できます。プラス記号を付けた要素の総和を P
-
Pythonで文字列内のすべてのAをBより前に配置するために必要な最小削除文字数を求めるプログラム
問題概要文字「A」と「B」の2種類のみで構成される文字列 s が与えられたとします。このとき、すべての「A」がすべての「B」よりも前に並ぶようにするために、文字列 s から削除する必要がある文字の最小数を求めるのが目的です。例えば、入力が S = "AABAABB" の場合、出力は 1 になります。最後の「A」を1つ削除すれば "AABBB" となり、すべての A が B より前に配置されるためです。解法のアプローチこの問題は、文字列を左から右へ一度走査しながら、各区切り位置において「削除が必要な文字数」を計算していくことで効率的に解けます。具体的には、
-
Pythonで連結リストを先頭と末尾から交互に並べ替える方法
片方向連結リスト(単方向リンクリスト)が与えられたとき、ノードを「末尾のノード → 先頭のノード → 末尾から2番目のノード → 先頭から2番目のノード…」という順序で並べ替えることを考えます。例えば、入力が [1,2,3,4,5,6,7,8,9] の場合、出力は [9, 1, 8, 2, 7, 3, 6, 4, 5] となります。解決のための手順この問題は、以下の手順で解くことができます。現在のノード c を先頭ノードに設定し、値を一時保存するための空のリスト l を用意します。c が null でない間、c の値をリスト l の末尾に追加し、c を次のノードへ進めます。これですべてのノード
-
【Python】売却後の待機期間ありで株売買の最大利益を求めるアルゴリズム
ある企業の株価が時系列順にリストで与えられたとき、その株の売買によって得られる最大の利益を求めることを考えます。ただし、以下の2つの制約があります。必ず買ってから売る必要がある(先に売ることはできない)売却した後は1日待たないと再度買えない(クールダウン期間が存在する)例えば、入力が prices = [2, 6, 9, 4, 11] の場合、出力は 11 となります。これは「2で買い → 6で売る → 1日待つ → 4で買い直す → 11で売る」という取引を行うことで、合計利益 11 を達成できるためです。解法のアプローチ:動的計画法(DP)この問題は、状態を2つに分けて管理する動的計画法で
-
Pythonで2次元バイナリ行列の最も左にある「1」の列インデックスを効率的に求める方法
問題の概要2次元のバイナリ行列(0と1のみで構成される行列)が与えられます。ここで、各行は昇順にソートされており、すべての0が1よりも先に並んでいるものとします。この条件のもとで、行列全体の中で最も左側に存在する「1」の列インデックスを見つけるプログラムを作成します。該当する「1」が存在しない場合は -1 を返します。例えば、次のような入力が与えられたとします。0001001100110010この場合、出力は 2 となります。なぜなら、3列目(インデックス2)に、行列全体で最も左に位置する「1」が存在するからです。解法のアプローチこの問題は、右上の角から探索を開始し、条件に応じて左または下へ移
-
Pythonで同じセットビット数を持つ次に大きい数を見つけるプログラム
数値 n が与えられたとき、2進表現における1の個数(セットビット数)が n と同じで、かつ n より大きい最小の数を求める問題を考えます。 例えば、入力が n = 7 の場合、出力は 11 になります。7 を2進数で表すと「0111」ですが、1が3つという条件を保ったまま 7 より大きい最小の数は、2進数で「1011」、すなわち10進数の 11 だからです。 解法のアプローチ この問題はビット操作を利用することで効率的に解けます。手順は以下の通りです。 copy に n を代入し、zeros と ones を 0 で初期化します。 copy が 0 ではなく偶数である間、次の処理を繰り返し
-
Pythonで最後に風船を受け取る子供の開始インデックスを求める方法
n人の子供が円形に並んでいて、順番に風船を受け取る場面を考えてみましょう。配布はk番目の子供(最初のインデックスは0)から始まり、風船をもらった子供はその場で円から外れます。その後も時計回りにk番目ごとの子供へ風船が渡され、最後に残った1人の子供が風船を受け取ります。ここで、nとkが与えられたとき、最後に風船を受け取る子供の開始インデックスを求めるのがこの問題です。具体例で理解する例えば、入力が n = 3、k = 2 の場合を考えてみます。1回目: 子供2が風船を受け取り、円から外れます。残りは [0, 1] になります。2回目: 子供0が風船を受け取り、円から外れます。残りは [1] だけ
-
【Python】リスト内の数値の0ビットをk回1に変更して最小の合計を求める方法
数値のリスト nums と整数 k が与えられたとします。私たちが行うのは、次の操作をちょうど k 回繰り返すことです。リストから任意の数値を1つ選び、その数値の2進表現の中で「0」になっているビットを1つ選んで「1」に変更します。すべての操作を終えた後の全要素の合計として考えられる最小値を返してください。答えが非常に大きくなる場合は、10^9+7 で割った余りを結果として返します。 例として、nums = [4, 7, 3]、k = 2 の場合を見てみましょう。各数値の2進表現は、4 が 100、3 が 011、7 が 111 です。2つのビットを「1」に設定する必要がありますが、合計の増
-
Pythonで爆弾の爆発時に安全なマスの数を求めるプログラム
2次元のバイナリ行列(0と1だけで構成された行列)を考えてみましょう。ここで、1は爆弾が置かれているセル、0は空のセルを表します。爆弾が爆発すると、その爆弾と同じ行および同じ列上にあるすべてのマスが被害を受けます。このとき、爆発の影響を受けずに安全に立てるマスの数を求めるのが課題です。例えば、入力が以下のような行列だったとします。110000000この場合、出力は 2 になります。なぜなら、右下のセルと中央右のセルの2箇所だけが爆発の影響を受けない安全な場所だからです。解き方のアプローチこの問題は、以下の手順で効率よく解くことができます。r := 行列の行数と同じサイズのリストを作成し、すべて
-
Pythonで手数料を考慮した株式売買の最大利益を求めるプログラム
ある企業の時系列順に並んだ株価リストと、1回の売却取引にかかる手数料が与えられているとします。この株を何度でも自由に売買した場合に得られる最大の利益を求めるのが本記事の目的です。ただし、売却する前に必ずその株を購入していなければならないという制約があります。問題の例たとえば、入力が prices = [2, 10, 4, 8]、fee = 3 の場合を考えてみましょう。このときの出力は 6 になります。まず 2 で株を買い、10 で売却します。手数料として 3 がかかるため、利益は 10 − 2 − 3 = 5 です。次に 4 で再度株を買い、8 で売却します。ここでも手数料 3 がかかるため