【Python】桁の配列から最小の数を作り、先頭と末尾の桁でできる数が素数かどうか判定する方法
問題の概要
0〜9の数字だけを要素に持つ配列 digits が与えられます。まず、これらの桁をすべて使って作れる最小の数を求めます。次に、その数の先頭の桁と末尾の桁を組み合わせてできる2桁の数(順方向・逆方向の2通り)が素数かどうかを判定し、生成した数と素数の結果を出力します。
たとえば、入力が digits = [5, 2, 1, 7] の場合を考えてみましょう。桁を昇順に並べると最小の数は 1257 になります。先頭と末尾の桁は「1」と「7」なので、組み合わせは 17 と 71 の2つ。この2つはどちらも素数であるため、プログラムは 1257、17、71 を返します。
解法のアプローチ
最小の数を作る基本は、各桁の出現回数を数えたうえで小さい桁から順に並べることです。全体の流れは以下のとおりです。
- 出現頻度の集計: 各数字(0〜9)が何回現れるかを辞書(マップ)に記録します。
- 最小数の構築: 0から9までの順に、記録された回数だけ桁を文字列へ連結していきます。
- 2桁の数の生成: 完成した数の先頭と末尾の桁を取り出し、「先頭+末尾」「末尾+先頭」の2通りの整数を作ります。
- 素数判定: それぞれの数について素数かどうかを調べ、結果に応じて値を返します。
素数判定について
素数判定にはシンプルな試し割り法を使用します。2から num−1 までの整数で順に割り、1つでも割り切れる数があれば素数ではないと判断します。今回は2桁の数しか判定しないため、この方法で十分高速です。
Pythonでの実装例
from collections import defaultdict
def isPrime(num):
if num > 1:
for i in range(2, num):
if num % i == 0:
return False
return True
return False
def solve(arr):
# 各桁の出現回数を集計
digits_freq = defaultdict(int)
for i in range(len(arr)):
digits_freq[arr[i]] += 1
# 小さい桁から順に連結して最小の数を作る
number = ""
for i in range(0, 10):
for j in range(digits_freq[i]):
number += str(i)
# 先頭+末尾 / 末尾+先頭 の2つの数を生成
num = int(number[0] + number[-1])
rev = int(number[-1] + number[0])
if isPrime(num) and isPrime(rev):
return int(number), num, rev
elif isPrime(num):
return number, num
elif isPrime(rev):
return number, rev
else:
return False
digits = [5, 2, 1, 7]
print(solve(digits))
入力
[5, 2, 1, 7]
出力
(1257, 17, 71)
コードのポイント
- defaultdict(int): 存在しないキーにアクセスすると自動的に 0 で初期化されるため、出現回数のカウントを簡潔に書けます。
- number[0] と number[-1]: Pythonの文字列インデックスを活用すれば、先頭の桁と末尾の桁を簡単に取得できます。
- 戻り値の分岐: 両方が素数なら3つの値、片方だけが素数なら2つの値、どちらも素数でなければ False を返します。
計算量について
桁の並べ替え部分は各桁を一度ずつ処理するため O(n)(n は桁の個数)、素数判定は試し割り法により最大 O(k)(k は判定対象の数)です。本記事のように2桁の数しか判定しない場合、実用上はきわめて高速に動作します。
-
Pythonで数値が二面素数(Dihedral Prime)かどうかを判定する方法
ある整数nが与えられたとき、それが「二面素数(dihedral prime)」であるかどうかを判定する方法を解説します。二面素数とは、その数自体が素数であり、さらに7セグメントディスプレイに表示した際に、表示の向き(通常の向きでも上下逆さまでも)に関わらず、同じ数または別の素数として読み取れる数のことです。例えば、入力がn = 1181の場合、出力はTrueになります。下の数字は上の数字を上下逆さま(180度回転)にして表示したものであり、どちらも素数となっています。アルゴリズムの手順この問題を解くために、以下の手順で進めます。up_side_down() 関数を定義します。引数としてnを受け
-
Pythonで素数を判定するプログラムの書き方を徹底解説
はじめに この記事では、「与えられた数値が素数かどうかを判定する」という問題に対する解決策を、Pythonのコード例とともにわかりやすく解説します。 問題の概要 問題設定:ある数値が与えられたとき、その数が素数であるかどうかを判定するプログラムを作成します。 まず「素数」の定義をおさらいしましょう。1より大きい正の整数のうち、1とその数自身以外に約数を持たない数を素数(そすう)と呼びます。たとえば、2、3、5、7などはそれ以外の約数を持たないため、素数です。 プログラムの考え方 今回作成するプログラムでは、入力された数値が素数かどうかを以下の手順で判定します。 1以下の数値は素数ではない