hack のためのネタ帳, etc,,,

状況

プログラミングの課題を採点する関係で Python コードの類似性を計測したい状況が生じたので「source code similarity」でググてみたところ、以下のページを見つけた。
この中から以下の module を見つけた。
READEM に Compare to Moss とかいうセクションがあるんだけど、どうもこの分野では Moss ってのが有名なんだそうな。
ただし、Moss は Stanford で運営されてるインターネットサービスなんだそうで、無料で利用可能なのだけれど、アカウント申請がメールで問い合わせなのと、コードをサーバーに放り投げる必要があり、更に投げて解析した結果は公開され URL の秘匿のみで保護されるようなので、ちょっと使い辛い。

で、上記の pycode_similar をざっと見てみるととてもコンパクトなスクリプトになってて、どうも Python 標準ライブラリの ast モジュールを使って、AST (Absolute Syntax Tree: 抽象構文木) 構築して AST レベルで比較しているっぽい。

なんか ast.parse(python_source_code) でサクッと AST 構築出来てるの羨まし過ぎる。こういうモジュールが標準で附属してるのは Python 強い。

ここまで手軽だと他にもありそうなので、「python ast similarity」でググってみたら、以下のページを見つけた。
pycode_similar は 1:1 比較しかできないのに対して、pyastsim は任意の数のファイル与えて一気に総当たり検索してくれるので、よりお手軽度が高い。

とりあえず、どちらも AST レベルで比較することで、変数名の違いは無視して類似性を比較してくれて、
例えば、

a/factorial.py

def factorial(n):
    sum = 1
    for i in range(n, 1, -1):
        sum *= i
    return sum

b/factorial.py

def factorial(n):
    v = 1
    for i in range(n,1,-1):
        v *= i
    return v
は類似度 100% として以下のように認識される。
$ pycode_similar a/factorial.py b/factorial.py
ref: a/factorial.py
candidate: b/factorial.py
100.00 % (18/18) of ref code structure is plagiarized by candidate.
candidate function plagiarism details (AST lines >= 4 and plagiarism percentage >= 0.5):
1.0 : ref factorial<5:0>, candidate factorial<5:0>
$ pyastsim a/factorial.py b/factorial.py
Detected pair similarity of 100% with edit distance of 0 for a/factorial.py and b/factorial.py

for ループ使ってるのに range() で降順に乗算してるのはちょっと独特だけど、まぁ典型的な書き方の範疇と言えなくはないし、仮に写したとしても申し訳程度に変数名は変えていてデッドコピーじゃないのでこれはまぁいいのかなとは思うが、どこで線を引くかは微妙である。
そういう微妙な判断は、コードの中身を目で見て比較しないと出来ないので、ちょっと面倒ではあるが仕方がないところ。
とりあえず、比較結果一覧から Graphical diff (meld や tkdiff, WinMerge 等) に食わせる UI あると捗りそうかな?

まじめにやるの面倒だけど、以下のような感じで、terminal 2 枚開いてコピペ方式だとコスト低いかな?
diffsim () { find . -iname "$1"  -exec pyastsim "${OPT[@]}" {} + | sed -E 's@(.*) for ./(.*) and ./(.*)@meld "\2" \"\3" # \1@g;/^$/d' | grep -E '[0-9]*%|[0-9]*$'; }; OPT=( --threshold 0 ) ; diffsim factorial.py

未評価

試してはないけど、他にも PyPI で「plagia」で検索すると幾つか見つかる模様。

コメントをかく


「http://」を含む投稿は禁止されています。

利用規約をご確認のうえご記入下さい

Wiki内検索

フリーエリア

管理人/副管理人のみ編集できます