トップに戻る

馬番と出走数から枠番を出す数式とVBA関数

競馬の枠番ってどうやって計算するんじゃろなと考えながら、こんなものが出来上がりました。

VBAの標準モジュールにOption Explicitから始まるコードをコピペした後、ワークシートのセルにこの関数を使用する数式を入れれば、枠番を出してくれます。

MITライセンスにするため、前置きのコメントが長いですがご容赦ください。

このプログラムについてのご質問やツッコミがありましたら、ツイッターやメールでお願いいたします。

プログラムバージョン:1.001 変数名や処理を微妙に変えました。返り値をVariantにして、不正な値を入力した時に#NUM!を返すようにしました。

プログラムバージョン:1.002 For文でゴリ押ししていたのを、シンプルな数式に変更。

プログラムバージョン:1.003 その他のエラーメッセージが表示されない状態だったので修正。

数式

MathJaxの調子が悪いので、数式を画像にしました。

Option Explicit

' GetBracketNum関数 番号と出走数から枠番を出す関数
' Copyright (C) 2020-2023 マヴユーユ (twitter:mavyuuyu)
' このプログラムのライセンスは、MIT Licenseです。
' This software is released under the MIT License.
' http://opensource.org/licenses/mit-license.php
' MIT Licenseの日本語訳は、以下のURLをご参照ください。
' https://ja.osdn.net/projects/opensource/wiki/licenses%2FMIT_license
'
' ******************** 使い方 ********************
' この関数は、シート上のセルでも計算することが出来ます。
' 数式例1・競馬の場合: =GetBracketNum(馬番, 出走数)
' 数式例2・競輪9車立ての場合: =GetBracketNum(車番, 9, 6)
' 枠数は省略すると、8が指定されます。
' ************************************************

Private Const ERR_INVALID_NUM = 10001

Public Function GetBracketNum( _
    ByVal num As Long, _
    ByVal entries As Long, _
    Optional ByVal brackets As Long = 8 _
) As Variant
    
    On Error GoTo ErrorHandler
    If Not IsValidNum(num, entries, brackets) Then
        Err.Raise ERR_INVALID_NUM
    
    ElseIf entries <= brackets Then
        GetBracketNum = num
        Exit Function
    
    ElseIf CalcLowerBracket(num, entries, brackets) <= _
           CalcLowerLimit(entries, brackets) Then
        
        GetBracketNum = CalcLowerBracket(num, entries, brackets)
        Exit Function
    
    Else
        GetBracketNum = CalcHigherBracket(num, entries, brackets)
        Exit Function
    
    End If
    
ErrorHandler:
    If Err.Number = ERR_INVALID_NUM Then
        GetBracketNum = CVErr(xlErrNum)
        Exit Function
    End If
    
    MsgBox "エラーが発生しました。" & vbCrLf & _
           "エラー番号:" & Err.Number & vbCrLf & _
           Err.Description
    Exit Function
End Function

Private Function CalcLowerLimit(ByVal entries As Long, _
                                ByVal brackets As Long) As Long
    
    CalcLowerLimit = brackets - (entries Mod brackets)

End Function

Private Function CalcLowerBracket(ByVal num As Long, ByVal entries As Long, _
                                  ByVal brackets As Long) As Long
    CalcLowerBracket = _
        WorksheetFunction.RoundUp( _
            num / WorksheetFunction.RoundDown(entries / brackets, 0), 0)

End Function

Private Function CalcHigherBracket(ByVal num As Long, ByVal entries As Long, _
                                   ByVal brackets As Long) As Long
    Dim base As Long
    base = WorksheetFunction.RoundDown(entries / brackets, 0)
    
    Dim a As Long
    a = WorksheetFunction.RoundUp( _
            (num - CalcLowerLimit(entries, brackets) * base) / (base + 1), 0)
        
    CalcHigherBracket = CalcLowerLimit(entries, brackets) + a
End Function

Private Function IsValidNum( _
    ByVal num As Long, _
    ByVal entries As Long, _
    ByVal brackets As Long _
) As Boolean
    If num > 0 And _
       entries > 0 And _
       brackets > 0 And _
       entries >= num Then
        IsValidNum = True
        Exit Function
    Else
        IsValidNum = False
        Exit Function
    End If
End Function
      

数式として使用するには、標準モジュールに上記のプログラムをコピペした後、以下のように数式を入力します。