AI から統計処理の提案を受けるのはどう?
はじめに
統計解析を行うとき、データファイルがあって何を調べたいかは決まっているけど、どの統計手法を使うのが良いかわからないことがあると思います。
周囲に統計に詳しい人がいればいいですが、なかなかそうもいきません。
そのようなときに、AI に質問すればもしかすると適切な手法を考えてくれるのではないかと期待して作ったのがこのツールです。
https://emuyn.net/stats/get_ai_proposal
Reactive stat
ベースとなっているのは、弊社が開発し提供している、Reactive stat というブラウザだけで使える統計アプリです。
信頼性の高い R で統計解析し、その結果を AI が解説します!
医療統計でよく使われる範囲をカバーしています。
生成AIがよしなにデータ分析してくれる未来はすぐそこにあるけど?
CSV を Chat GPT4 や Claude3 にアップロードして、プロンプトで指示を出すと解析までやらせることはすでに可能です。
でも、診療情報から取得したデータを医療者が解析して論文や学会発表するとき、AIに全面的に頼ることは許されません。
- 医療データは個人情報を含むので、うかつに送信できない
- AI が解析したデータは信頼性がないので論文や学会では使えない
などの理由です。
医者は統計に詳しいんじゃないの?
別記事でも書きましたが、統計は一応は授業で習いますが、全員が詳しいとは限りません。
例えば、癌の術後の Overall Survival の計算における、交通事故で亡くなられた患者さんの扱いを医師に聞いてみると、おおよそ半分は間違えてましたね(実体験)。
また、医療統計は医師のみが使うものではありません。看護師さんも看護研究で使います。せっかく素晴らしい研究をしたのに、統計処理をどうやっていいかわからないから発表を断念することもありがちです。
誰かの役に立ちたい
というわけですので、少しは役に立つかと思い、弊社の ブラウザだけで使える無料統計ソフト Reactive Stat に、AI に統計処理を提案させる機能 をつけてみました。
質問すれば適切な手法を提案してくれる (かも)。
注意して使ってください
実験的機能で実用性はまだまだかもしれませんが、少しだけ未来を感じさせてくれます。
でも、注意して使ってくださいね。
最終的な統計解析は、完璧に理解してから行うか、専門家の指導を仰ぐようにお願いします。
AI へのプロンプト
以下のプロンプトを Anthropic Claude-3-haiku API に投げました。
共通の system prompt には、統計アプリで実行可能な統計処理のリストと、その実行ページへのリンクが記載されています。
あなたは統計学者である。
ユーザは、統計に関して知識がなく、データを持っているが、どのような統計手法が適切かわかっていない。
ユーザからデータの各項目の情報が与えられ、ユーザが何を調べたいのかが提示されるので、適切な統計手法を提案せよ。
出力フォーマットは、次の xml を用いること。
<proposal>
<method></method>
<reason></reason>
</proposal>
{{json形式の統計手法リスト}} を読んで、どのような統計手法が実施可能かを理解し、それぞれにどのようなデータタイプが適切かを把握せよ。
ユーザから与えられたデータの各項目の情報を詳細に検討し、適切な統計手法を method から選択せよ。
数値データの場合は、データの分布を認識し、パラメトリックと非パラメトリックのどちらが適切かを考慮せよ。
数値でないカテゴリカル変数の場合は、群分類に用いるか、統計的モデリングを適用することを考慮せよ。
なお、 {{json 形式のリスト}} における methods は method の配列である。
適切な method が複数ある場合や、さらに詳細な分析が必要と考えられるときは、method ごとに <proposal> を作成せよ。
<proposal> は必ず必要で、その数は多いほどよい。
それぞれの <proposal> の中で、method をそのままの形で <method></method> に記載し、
なぜその method が良いと考えるのか理由を、詳しく<reason></reason>に記載せよ。
最後に、統計手法をどのような順序でどのような考えに基づき適用すべきかを、詳しく<conclusion></conclusion>に記載せよ。
適用可能な統計手法の {{json形式の統計手法リスト}} は以下の通り。
[
{
"category": "名義変数の解析",
"items": [
{
"label": "1標本の比率の検定",
"methods": ["1標本の比率の検定"],
"link": "https://www.emuyn.net/stats/one_sample_proportion_test"
},
{
"label": "分割表の作成と群間の比率の比較",
"methods": ["カイ二乗検定", "Fisherの正確確率検定"],
"link": "https://www.emuyn.net/stats/two_way_table"
},
{
"label": "対応のある比率の比較(McNemar検定)",
"methods": ["McNemar検定"],
"link": "https://www.emuyn.net/stats/mcnemar_test"
},
{
"label": "対応のある3群以上の比率の比較 (Cochran Q 検定)",
"methods": ["Cochran Q 検定"],
"link": "https://www.emuyn.net/stats/cochran_q_test"
}
]
},
{
"category": "連続変数の解析",
"items": [
{
"label": "1標本の平均値のt検定",
"methods": ["1標本の平均値のt検定"],
"link": "https://www.emuyn.net/stats/single-sample_t-test"
},
{
...
user content には、ユーザーが入力する "何を調べたいのか" の文章と、対象とするデータの各カラムの情報を入れます。
promptText
がユーザーからの文章ですが、一応ユーザー sanitizeInput() でタグの除去などしてあります。
targetColumnsInfo
には、事前に読み込んだデータの特徴量 (サンプル数、平均値、中央値、など) が入っています。
ここで重要なのは、生データは送信しないということです。
これによって、個人情報が流出することを防ぎます。
そもそもデータの概要 (各カラムの特徴量) がわかれば十分ですし、生データを送ると AI token が膨大になってしまい処理時間がかかってしまいます。
const content = sanitizeInput(promptText) +
"以下のjsonは各カラムの情報である。" +
JSON.stringify(targetColumnsInfo);
各カラムの特徴量 (targetColumnsInfo
) は、事前にブラウザ内で計算してからAIに投げます。
{
"T Stage": {
"type": "categorical",
"val": {
"T3": {
"frequency": 50,
"proportion": 0.12406947890818859
},
... 中略 ...
"T4": {
"frequency": 13,
"proportion": 0.03225806451612903
}
},
"frequency": {
"T3": 50,
"T2": 180,
"T1": 160,
"T4": 13
}
},
"N Stage": {
"type": "categorical",
"val": {
"N2": {
"frequency": 78,
"proportion": 0.1935483870967742
},
... 中略 ...
},
"腫瘍サイズ": {
"type": "continuous",
"val": {
"number of numeric data": 403,
"minimum value": 1,
"first quartile": 15,
"median value": 24,
"third quartile": 36,
"maximum value": 120,
"interquartile range": 21,
"outliers": [
68,
... 中略 ...
120
],
"average value": 29.833746898263026,
"variance": 417.3379627915012,
"standard deviation": 20.428851235238394,
"sample variance": 416.3023847200582,
"sample standard deviation": 20.40348952311977,
"standard error of mean": 1.0176335644243124,
"skewness": 1.6986987220553404,
"kurtosis": 6.401239735413369
}
}
... 中略 ...
}
ユーザーが入力する "何を調べたいのか" の文章 (promptText
) はこんな感じで入力してもらいます 。
"T Stage", "N Stage", "遠隔転移", "腫瘍サイズ", "組織型", "ER", "PR" から "転移リンパ節個数" が予測できるか調べたい
これらをまとめて、Anthropic Claude-3-haiku API に投げます。
本当は Claude-3-opus のほうが精度が高いのかもしれませんが、token が多くなるので、無料サービスではとても賄えません。
で、この例の場合に得られたAIからの提案は以下の通り。
まず、散布図行列やPearsonの相関係数を用いて変数間の相関関係を確認します。次に、線形混合効果モデル(LMM)を構築し、各説明変数の固定効果と随伴効果を推定します。
LMMの結果から、転移リンパ節個数に最も影響を与える変数を特定し、その変数に着目して詳細な分析を行います。必要に応じて、ロジスティック回帰モデルなどの他の多変量解析手法も適用し、より包括的な分析を行うことが望ましいでしょう。最終的には、これらの分析結果を総合的に評価し、転移リンパ節個数を予測するための最適なモデルを提案します。
多変量解析
この問題では、複数の説明変数(T Stage、N Stage、遠隔転移、腫瘍サイズ、組織型、ER、PR)から目的変数(転移リンパ節個数)を予測したいため、多変量解析が適切です。多変量解析を行うことで、各説明変数が目的変数に与える影響の大きさを評価し、最も重要な説明変数を特定することができます。また、説明変数間の交互作用も考慮することができるため、より正確な予測モデルを構築できます。
線形混合効果モデル(LMM)
転移リンパ節個数は連続変数であり、正規分布に従うと仮定できます。一方、説明変数の多くがカテゴリカル変数であるため、線形回帰モデルを適用するのは適切ではありません。そこで、線形混合効果モデル(LMM)を使用することで、カテゴリカル変数と連続変数を同時に扱うことができます。LMMでは、固定効果と随伴効果を組み合わせることで、より複雑なデータ構造を適切にモデル化できます。この問題では、患者ごとの個体差を考慮する必要があるため、LMMが適切な手法だと考えられます。
いろいろ提案してくれました。読んでいるとわかったような気になります。線形混合効果モデル(LMM) は最近流行ってますよね。
実際の操作と画面
解析したいデータは CSV やエクセルから読み込むことができます。
分析対象のカラムは必要なものだけ選択します。
選択するとミニヒストグラムと特徴量が表示されますのでデータへの理解が深まります。
Reactive stat では、データの内容を視覚的に理解しながら解析が進められるように工夫してありますので、ぜひ使ってください!
結果はポンコツロボット君から。AI に描かせましたが、かわいいので気に入ってます。
引き続き統計処理へ!
AIからの提案の多変量解析や線形混合効果モデル(LMM)へのリンクをクリックすると、対応するページが開いて、解析を行うことができます。
この例のように、質問内容に応じて複数の提案がなされますので、あとはユーザーに考えていただくことになります。
工夫した点など
シームレスな利用のためにリンクを用意する
単に "適切な手法" を答えさせるだけでは、実際にこのウェブアプリで処理できない手法を提案されてしまい、ユーザーは行き詰まってしまいます。
あくまで、統計に詳しくないユーザーへのアシスト機能ですから、シームレスに解析へ行けなくてはなりません。
そこで、統計手法リストを事前に与えておき、この中から選択させることにしました。
Anthropic Claude-3-haiku の選定理由
Claude-3は、xml を理解し、指示に従って特定の tag に出力してくれるので、出力を利用した後処理が非常に簡単になります。
やり方の問題かもしれませんが、他の AI API ではうまくゆきませんでした。
もちろん、生成される文書の質、生成速度、価格も重要です!
生成AIによしなにデータ分析してもらうのに勝る点は?
Reactiva stat では、統計解析は信頼性の高い R で実行しますので、論文などにはそのように書くことができます。
統計のプロが手助けした場合と同じ表記ができる、というわけ。
この解析は R version 4.4.0 (2024-04-24) にて行いました
などです。