関数やメソッドのソースの平均行数
Posted feedbacks - Nested
Flatten HiddenSqueak Smalltalk で。
Smalltalk ではメソッドもオブジェクトで、そのソースはメソッドオブジェクト(CompiledMethod のインスタンス)の属性であるかのような扱いになっています。したがって、各メソッドに問い合わせ(getSource)て得られたソースコードの行数(lineCount)を列挙し、その平均(average)を出せば、今回調べたい平均行数が求まります。
1 2 3 4 5 | | numsOfLines |
numsOfLines := CompiledMethod allInstances collect: [:each | each getSource lineCount].
^{#調査メソッド総数-> numsOfLines size. #平均行数 -> numsOfLines average asFloat}
"=>{#調査メソッド総数->42237 . #平均行数->8.37561853351327} "
|
新年明けましておめでとうございます。 最初は頑張ってC言語で作れないかやってみたのですが、関数名にマクロが 使われている等の理由で8割程度しか把握できませんでした。仕方がないのでVS2008 のマクロ機能を使ってやってみました。 対象は、"C:\Program Files\Microsoft Visual Studio 9.0\VC\crt\src"にあった 拡張子が"*.c"のファイル全てです。空のプロジェクトを作成し、これらのファイルを ソースファイルとして取り込んでから、このマクロを実行すると結果が表示されます。 一応、VC++で使われているC言語ソースという限定的な条件ですが... <調査対象のファイル> _ctype.c _filbuf.c _file.c _filwbuf.c _flsbuf.c _flswbuf.c ... <調査対象の関数> _Getcvt: 9 _Wcrtomb: 54 __Wcrtomb_lk: 10 __iscsym: 6 _iscsym_l: 7 __iscsymf: 6 _iscsymf_l: 7 ... <結果> 調査ファイル総数: 708 調査関数総数: 1359 平均行数: 36.3951434878587
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 | Imports System
Imports EnvDTE
Imports EnvDTE80
Imports EnvDTE90
Imports System.Diagnostics
Imports Microsoft.VisualStudio.VCCodeModel
Public Module CFunctionEnumeration
Dim numberOfFiles As Integer
Dim numberOfFunctions As Integer
Dim totalLines As Integer
' 色々と処理が面倒なので例外にしてしまった。
Private Class OutputPainNotExistException
Inherits Exception
Public Sub New(ByVal message As String)
MyBase.New(message)
End Sub
End Class
Private Function GetOutputPane() As OutputWindowPane
' 結果を表示するペインを作成して返す。
Const titleOfPain As String = "関数調査の結果"
Static Dim isPainCreated As Boolean = False
Dim pains As OutputWindowPanes = DTE.ToolWindows.OutputWindow.OutputWindowPanes
If isPainCreated = False Then
For Each p As OutputWindowPane In pains
If p.Name = titleOfPain Then
GoTo ALREADY_CREATED
End If
Next
If pains.Add(titleOfPain) Is Nothing Then
Throw New OutputPainNotExistException(titleOfPain & "ペインは存在しません。")
End If
ALREADY_CREATED:
isPainCreated = True
End If
GetOutputPane = pains.Item(titleOfPain)
End Function
Private Sub OutputString(ByRef s As String)
GetOutputPane().OutputString(s)
End Sub
Private Sub OutputSourceFiles()
' ソースファイル名を出力する。
Dim projectFolders As ProjectItems = DTE.Solution.Item(1).ProjectItems
For Each i As ProjectItem In projectFolders
If i.Name = "ソース ファイル" Then
Dim sourceFileFolder As ProjectItems = i.ProjectItems
For Each j As ProjectItem In sourceFileFolder
OutputString(j.Name & vbCrLf)
numberOfFiles = numberOfFiles + 1
Next
End If
Next
End Sub
Private Sub OutputFunctions()
' 関数名とソースコードの行数を出力する。
Dim codeModel As VCCodeModel = DTE.Solution.Item(1).CodeModel
For Each f As VCCodeFunction In codeModel.Functions
Dim lines As Integer = f.EndPoint.Line() - f.StartPoint.Line() + 1
OutputString(f.Name & ": ")
OutputString(lines & vbCrLf)
numberOfFunctions = numberOfFunctions + 1
totalLines = totalLines + lines
Next
End Sub
Private Sub OutputResult()
OutputString("調査ファイル総数: " & numberOfFiles & vbCrLf)
OutputString("調査関数総数: " & numberOfFunctions & vbCrLf)
OutputString("平均行数: " & (CDbl(totalLines) / numberOfFunctions) & vbCrLf)
End Sub
Private Sub Reset()
numberOfFiles = 0
numberOfFunctions = 0
totalLines = 0
End Sub
Public Sub OutputFunctionLength()
Try
Dim p As OutputWindowPane = GetOutputPane()
Reset()
p.Clear()
OutputString("<調査対象のファイル>" & vbCrLf)
OutputSourceFiles()
OutputString(vbCrLf)
OutputString("<調査対象の関数>" & vbCrLf)
OutputFunctions()
OutputString(vbCrLf)
OutputString("<結果>" & vbCrLf)
OutputResult()
p.Activate()
Catch e As Exception
MsgBox(e.Message, MsgBoxStyle.Critical)
End Try
End Sub
End Module
|
補足で、VSに理解できないように関数が記述されている場合は含まれません。あと、paneが痛いになってました...orz




sumim
#9747()
Rating0/0=0.00
イントロスペクションおよびメトリックスのお題です。
アジャイル界隈などでは、あまり長くだらだらと書いてはいけない…と言われている 関数 and/or メソッド ですが、ならば実際のところ、洗練された既存のライブラリにおいて、関数 and/or メソッド は平均すると何行くらいで記述されているのか…といった情報を具体的に把握しておきたいと思ったことはありませんか?
そこで、みなさんイチオシの言語それ自身で書かれているライブラリを、それなりの規模になるように集めてきて、1)集めたライブラリ群内に定義されている全 関数 and/or メソッド の合計数(母集団の確認のため)、と 2)関数 or メソッドのソースの平均の行数、を求めるコードと、その結果を示してください。
なお、関数 and/or メソッドに帰属するものであれば、コメント行やアノテーションのたぐいも行数のカウントに含めてください(コードが必要以上に複雑にならない範囲で結構です)。また、関数内関数定義やメソッド内クラス定義(ひいてはその中でのメソッド定義)といった入れ子になったコードの行数をどう解釈するかの判断はお任せします。関数とメソッドが共存する言語では両者を区別してカウントする必要はありません(しても構いません)。平均値を求めるコードを、対象言語で記述することが技術的に困難な場合は、UNIX的なツールを組み合わせたり、IDEなどが提供するメトリックス機能を活用して算出した結果を示すのでもよいと思います。
このお題は、平均行数が 8.4 行(Squeak Smalltalk の組み込みライブラリ+αより、調査メソッド総数 4万)と、一般に簡潔さが美徳とされている Smalltalk からの挑戦(?)でもあります。
[ reply ]