DESIGN / CODE / INFRA / AI

解説

AIのJSONに同じキーが二つある?読み込み後に消える重複を検出しよう

JSONとして読めても、同じオブジェクトの重複キーが後の値へ置き換わる場合がある。Pythonの読み込み時に検出する小さな例で確認する。

AIのJSONに同じキーが二つある?読み込み後に消える重複を検出しよう
保存リストを見る →
この記事の道しるべ 4項目

AIが返したJSONにcountが二つあった。読み込んだ後の辞書には一つしかないので、問題なしと判断してしまわないようにしよう。重複キーは、読み込み時に失われることがあるよ。

今回はPython 3.12で、短い架空のJSON文字列を確認する。実際の顧客データやAPIへの送信は必要ない。モデルの出力を実測した記事ではなく、受け取ったデータを検査する練習だよ。

普通に読むと後の値が残る

import json

raw = '{"count": 2, "count": 5}'
print(json.loads(raw)) # {'count': 5}

Pythonの標準jsonでは、同じ名前が繰り返される場合、通常は最後の値が残る。読み込んだ辞書だけを検査しても、元にcountが二つあったことは分からなくなるんだ。

受け取れるから問題がない、と判断せず、重複をどう扱うかを自分の仕様として決めよう。異なる実装が同じ扱いをするという前提にも立たないほうがよいね。

読み込み時のペアの列で検出する

import json

def unique_object(pairs):
    result = {}
    for key, value in pairs:
        if key in result:
            raise ValueError(f"キーの重複: {key}")
        result[key] = value
    return result

raw = '{"count": 2, "count": 5}'
try:
    data = json.loads(raw, object_pairs_hook=unique_object)
except ValueError as error:
    print(error)

object_pairs_hookは、オブジェクトを読み込むときの名前と値のペアを受け取る仕組み。今回の例では辞書へまとめる前に、同じキーがあったら止める。

期待する表示は「キーの重複: count」。入れ子のオブジェクトにもこの処理が使われるので、内側の重複も検査できるよ。

同じ名前が別の場所にある場合とは分ける

{"before": {"count": 2}, "after": {"count": 5}}

この二つのcountは、別のオブジェクトの中にある。今回の「同じオブジェクト内の重複」とは違い、検査を通る例だよ。

また、配列の中のレコードで同じIDが繰り返される問題も別。名前と値の構造を読むことと、レコードの一意性を確かめることは、必要な段階が違う。

型や必須項目の確認も別に行う

重複がなくても、countが文字列だったり、必要な項目がなかったりするかもしれない。今回の関数は、そのすべてを検証するものではない。標準外の数値の扱いなど、厳密なJSONとしての条件も別に点検しよう。

AIへの依頼にも「同一オブジェクト内のキーを重複させない」と書けるが、指示だけで検証を省かないようにしよう。内容を実行するevalなどで読む必要はないよ。

編集部では、重複したcount、入れ子の重複、別オブジェクトの同名キー、通常のオブジェクトをPython 3.12で確認した。すべてのJSON仕様や、各サービス固有の検証を置き換えるものではないよ。

基本の構文・型はJSONの確認、レコードの重複は識別キーの点検も合わせて見よう。

参考・出典

公開と変更の記録
  • :初回公開

日時は日本時間です。記載のある変更は、確認できた編集記録に基づきます。更新日の違いだけから変更内容を推測して載せることはありません。

更新・訂正の方針 →

みんなのコメント 0

感想や、試してみたことを聞かせてね。コメント・返信は承認後に公開されます。

最初のコメントをどうぞ。