🚌

LLMを用いて複数社の四半期報告書から共通の重要指標を特定させてみた

2024/12/27に公開

1. サマリ

  • 複数社の有価証券報告書(四半期報告書)のPDFを読み込ませLLMを噛ませることで、各社で重要と考えられるKPIの特定、業界共通で重要とされるKPIの特定を行いました
  • 実験の結果、LLM特有の表記揺れ等はあるものの、各KPIの特定が精度よくできました
  • 特定したKPIを元に数値を抽出し、競合分析等に繋げることが可能となりそうです


2. 背景

今回は有価証券報告書とLLMを絡め、人が読まずとも有用な情報を拾ってもらう可能性を探るべく実験を行ってみました。
背景としては大きく2点あります。

RQ➀:
有価証券報告書を読む際、長いため必要なところのみピックアップして読むことが多いが、実際がピックアップしなかった部分にも何かしらの有用な情報が含まれているのでは?

RQ➁:
有価証券報告書にはたくさんの情報が載っているが、どれが重要な指標なのかが分からない。会社ごと、業界特有のものなどさまざまな視点で、これらの特定をしてくれたら役に立つ場面が多いのではないか?



要は、「小さい文字ばっかりの100ページを超えた資料、詳細に読んでなんかいられるか!便利なツールがあるんだから機械にさせちゃおうぜ!」ということです。

また、今回の実験は 次のステップに繋げるためのきっかけの提示 という立ち位置を想定しています。指標の特定を行うことで、該当箇所のみ精読する、その指標の数値を抽出・蓄積し分析に用いる、などのネクストステップに繋げたいと考えています。


3. 実行環境

実験環境は以下の通りです。

  • プロセッサ:AMD Ryzen 5 3500U with Radeon Vega Mobile Gfx
  • メモリ:8.00GB
  • OS:Windows11
  • 言語:Python 3.12.3
    • 使用モジュール:anthropic, base64, time
  • LLM:Sonnet 3.5 (Anthropic社)


4. 実験内容・結果

4.1 使用したデータ

今回は下記のデータを使用しました。

企業の選定理由としては、

  • 同じ「小売業」と分類されること
  • 同じ業種でありつつも扱っている商材や業態が違うため、似た傾向が見られるのか気になった

というところでしょうか。
小売業を選んだのは、身近な他の業界より身近で重要そうな指標を想像しやすいかなと思ったからです。

また、今回の実験は「できるかどうか知りたい」「できるのであればざっくりどれくらいの精度なのか知りたい」というのが目的であるため、できるだけコストは抑えられるよう四半期報告書を用いています。


4.2 コード

今回まわしたコードは以下の通りです。

test.ipynb
import anthropic
import base64
import time

start_time = time.time()

# ローカルのPDFファイルを読み込む
pdf_path_ion = r"Your_pdfpath" #イオンの四半期報告書
pdf_path_nitori = r"Your_pdfpath" #ニトリの四半期報告書

with open(pdf_path_ion, "rb") as f:
    pdf_data_ion = base64.standard_b64encode(f.read()).decode("utf-8")
with open(pdf_path_nitori, "rb") as f:
    pdf_data_nitori = base64.standard_b64encode(f.read()).decode("utf-8")

# Anthropic API クライアントを作成
client = anthropic.Anthropic(
        api_key="Your_api_key"  # ここにAPIキーを入力
)

# Claude API リクエストの設定
message = client.beta.messages.create(
    model="claude-3-5-sonnet-20241022",  # 使用するモデル
    betas=["pdfs-2024-09-25"],  # 使用するベータ機能
    max_tokens=1024,  # 出力トークン数の上限
    messages=[
        {
            "role": "user",
            "content": [
                # 各PDFを個別のドキュメントとして渡す
                {
                    "type": "document",
                    "source": {
                        "type": "base64",
                        "media_type": "application/pdf",
                        "data": pdf_data_ion
                    }
                },
                {
                    "type": "document",
                    "source": {
                        "type": "base64",
                        "media_type": "application/pdf",
                        "data": pdf_data_nitori
                    }
                },

                # テキスト部分を追加
                {
                    "type": "text",
                    "text": (
                        "添付の資料は2つの企業の四半期報告書です。各社で重要と考えられる指標、両社ともで重要と考えられる共通の指標を特定してください。\n"
                        "下記フォーマットにしたがって結果を出力してください。"
                        "共通KPI:\n - KPI1(会社1での名称, 会社2での名称) \n - KPI2(会社1での名称, 会社2での名称) ...\n"
                        "補足:\n 必要に応じてKPIの名称や略語の説明を加えてください。\n"
                        "その他、文章中で共通して言及されており、KPIとして特定されていない指標があれば、それらも教えてください。\n"
                        "文章内にはカンマやクォーテーションを含めないでください。\n"
                    )
                }
            ]
        }
    ],
)

# 出力を表示
print(message.content)

end_time = time.time()
print(f"実行時間: {end_time - start_time:.2f} 秒")


PDFについて:

今回は、事前にローカルに保存したものを使用する形としました。
URLから直接持ってきてもよかったのですが、事前にPDFを加工する(特定のページのみ切り出す)ことも想定していたのでこの形となっています。
結果的にはPDFへの加工はしなかったので、URLから直接持ってきても大丈夫です。

リクエストについて:

今回は2社分のPDFを1リクエストで送ることとしました。
理由は大きく2点あります。

  • 「比較」に重点を置いている
  • 共通して重要とされる指標がほしかった

2.背景でも述べた通り、「上記コードにて指標名を取得 → それらの数字を拾い比較」 という流れを念頭においています。この流れに繋げるためには、出力する指標名を一般的な指標名ではなく、各社の指標名に合わせる必要がありました。
また、数字を拾わずとも重要視している指標を比較することで その会社が今何に重点を置いているのか というところも見えると考えています。
このような理由により、1リクエストで送るほうがよいと判断しました。プロンプトもこちらに合わせた形となっています。


4.3 結果

結果は以下の通りです。(見やすいように改行のみ行いました)

共通KPI:
- 売上高(営業収益, 売上高)
- 営業利益(営業利益, 営業利益)
- 経常利益(経常利益, 経常利益)
- 親会社株主に帰属する四半期純利益(親会社株主に帰属する四半期純利益, 親会社株主に帰属する四半期純利益)
- 総資産(総資産額, 総資産)
- 純資産(純資産額, 純資産)
- 1株当たり四半期純利益(1株当たり四半期純利益金額, 1株当たり四半期純利益)

イオン固有の重要指標:
- セグメント別営業収益
- ショッピングセンター内テナントの売上高
- グループ共通ポイントプログラムの会員数

ニトリホールディングス固有の重要指標:
- 店舗売上高
- 通販売上高
- 店舗数推移

その他の共通する重要な言及事項:
- 物流効率化への取り組み
- 原材料価格・コストの動向
- デジタル化・キャッシュレス決済の推進
- 海外展開の状況
- サステナビリティへの取り組み

実行時間: 20.88秒

全体的に妥当性は高そうとの印象です。
「共通KPI:売上高」を確認すると、会社ごとに指標名が異なっている場合もうまく拾ってきているように思います。

各社の固有の重要指標に関しては、個人で有価証券報告書を読む際にはあまり見ないであろう項目が並んでいますね。
イオン固有の指標を見てみると、「セグメント別営業収益」「ショッピングセンター内テナントの売上高」など、 テナントに入ってもらう というイオン特有の業態が見えるかなと思います。

ニトリ固有の指標をみると、「店舗数推移」という指標がピックアップされています。
四半期報告書の該当箇所を読むと、

  • 「住まいの豊かさを世界の人々に提供する」という企業理念に基づき、特に海外への出店を進めていること
  • 会社として「お買い上げいただけるお客様の数が増え続けることが社会貢献のバロメーターとなる」と考えていること

が記載されていました。だいぶ精度よく拾うことが出来ているのではないでしょうか。



結構精度がよさそうなので、他の業界ではどんな結果になるのか気になり、試してみることとします。
この業界はこれを見ろ!みたいなものが出せると有用そう。


4.4 実験➁:使用したデータ

使用したデータは以下の通りです。



今回は陸運業を取り上げることとします。
取り上げる理由は大きく2点です。

  • 「公共交通機関」という都合上、採算が取れない場合でも安易に「廃線」という決断をすることができないという特性があること
  • 電車・バスなど、小売業以上に設備関連のお金がかかっていることが予測されること

公共交通機関は大事なインフラの1つであるため、採算が取れない路線でも安易に廃線とすることはできません。そのぶん国や県、自治体からの補助金は交付されていますが、補助金を加えても黒字にならないような厳しい局面にいる会社さんも多くあるのが現状だそうです。

また、以前とあるバス会社の社長さんの講義を受けた際に、「バスを1台走らせる場合、お客様が乗っても乗らなくてもコストは変わらない、すなわち固定費である」ということをおっしゃっていて、なるほど!と思ったことも影響しているのかなと思います。
陸運業の場合、1台走らせると x 円、2台走らせると 2x 円、...という形となりますが、小売業の場合は、1日開店する場合、固定費[電気代、従業員1人] + 変動費[お客様にサービスを提供するのに必要な従業員の人数]というような形になります。

以上のような理由で陸運業を取り上げることとしてみました。


4.5 実験➁:コード

4.2より、読み込むPDFを変更しただけなので割愛します。


4.6 実験➁:結果

結果は以下の通りです。

共通KPI:
- 営業収益(東京メトロ 営業収益, 西日本鉄道 営業収益)
- 営業利益(東京メトロ 営業利益, 西日本鉄道 営業利益)
- 経常利益(東京メトロ 経常利益, 西日本鉄道 経常利益)
- 親会社株主に帰属する四半期純利益(両社同名)
- 1株当たり四半期純利益(両社同名)
- 総資産額(両社同名)
- 純資産額(両社同名)
- 自己資本比率(両社同名)

各社固有の重要指標:
東京メトロ:
- 運輸成績(輸送人員 定期/定期外)
- 旅客運輸収入(定期/定期外)
西日本鉄道:
- 国際貨物取扱高(航空輸出入 海運輸出入)
- セグメント別営業収益/利益(運輸業 不動産業 流通業 物流業 レジャー・サービス業)

その他の共通指標:
- 減価償却費
- のれんの償却額
- 設備投資関連指標
- 有利子負債

補足:
両社とも鉄道事業を中心としていますが、事業構造や重視する指標に違いが見られます。東京メトロは都市部の地下鉄事業に特化し輸送実績を重視する一方、西日本鉄道は多角化経営を展開しセグメント別業績を重視しています。

実行時間: 20.55秒

共通KPIに関しては、表記揺れは気になるもののうまく拾ってくることが出来ている印象です。
東京メトロ、西鉄ともに前述したような赤字の会社ではないものの、利益にこだわっている様子が読み取れます。

「その他の共通指標」は小売業とは大きく変化し、減価償却費などが挙げられています。これは陸運業ならではの特徴と言えそうです。内容自体は財務諸表で開示とのことで、四半期報告書ではなく有価証券報告書を読み込ませれば拾ってくることが可能かと考えます。

また、「補足」にもあるように、業態の違いが「各社固有の重要指標」から読み取れます。
東京メトロは陸運業のみで賄っている会社のため、運輸成績や運輸収入を重要視しており、西鉄は陸運業だけでなくストア事業、不動産事業なども行っているためセグメント別の営業収益を重視しているようです。
これらの違いより、例えばメトロ視点から西鉄を見る場合、 陸運業だけでなく他の業種にも手を出すことがリスクヘッジとして有用である というようなことが考えられます。コロナのような非常事態でもスーパーには行く必要があるし、家賃を払わなくてよいという事態にはなりません。そのため、陸運業の収益が落ちたとしても他の事業である程度の収益を担保することができるということは企業にとって大きなメリットです。


5. まとめ

LLMに四半期報告書を読み込ませることで、各社特有の重要指標・業界特有の重要指標の特定を行ってみました。
肌感覚としてはそれなりの精度で持ってきてくれそうだなと感じています。特定→その指標の値を抽出して蓄積・比較する、なども十分可能と考えています。

課題としては、トークン数の上限とコストです。読み込ませるPDFのページ数や企業数が多くなると、モデルの上限に引っかかってしまうようです(今回も実際に引っかかり、一度に扱う社数を3社から2社に減らしたという経緯があります)。PDFをそのまま読み込むのではなく分割する、OCR→テキスト化してから読み込むなど1ステップ挟む必要があるかなと考えています。

今後は、重要指標がなぜ重要と判断したのかも出力させること、重要指標の特定 → その指標の値の抽出・蓄積・比較などの1連の流れを1度に行うことのできるよう整えること、資料を1リクエストで入力させた場合と複数リクエストに分けて入力させた場合の比較なども行えたらよいと考えています。


宣伝

弊社ではデータ基盤やLLMのご相談や構築も可能ですので、お気軽にお問合せください。
https://solution.rounda.co.jp/

また、中途採用やインターンの問い合わせもお待ちしています!

https://www.wantedly.com/companies/company_5576351/projects

Discussion