文字列数式評価(3)~符号処理

普通の式であればかっこを外したあとに
3つ以上符号("+","-")が連なることはないだろうが、
念のためそれも考慮した処理を組み立てる。

"+"で区切ることを考えると、
最終的に残すべきなのは"+"と"+-"ということになる。

連続する符号のパターンは

"++", "--", "+-", "-+"

の4通りで現れる度に前2つを"+"、後ろ2つを"-"に置き換える。
最後に連続した符号がなくなったところで
"-"を"+-"に置き換えれば完成となる。

'   (数式の中の)符号処理
Private Function XEval_Sign(ByVal s) As String

    '   2つ以上連続している符号を処理する
    Do While XInStr(s, "++", "+-", "-+", "--")
        s = XReplace(s, "+", "++", "--")
        s = XReplace(s, "-", "+-", "-+")
    Loop
    '   単独の "-" を "+-" に変換
    s = Replace(s, "-", "+-")

    '   "*"、"/" の直後の "+" を削除
    s = Replace(s, "*+", "*")
    s = Replace(s, "/+", "/")

    XEval_Sign = s

End Function

最後の2つのReplaceがないと "3*-3" が変換後 "3*+-3" となり、
正しく項に分解できなくなるので必要である。

いちいちInstrやReplaceを重ねるのが面倒なので、
まとめて処理する関数も作っておく。
(他に使い道があればいいのだが)

'   機 能  :   拡張文字列検索
'   書 式  :   XInStr(s, [t()])
'   返り値  :   文字列 t() のうちいずれかが、
'               文字列 s の中に含まれてるとき True
'   引 数  :   s   -   文字列
'               t() -   検索する文字列

Public Function XInStr(s, ParamArray t()) As Boolean

    Dim i               As Long         '   繰り返し変数
   
    If UBound(t) < 0 Then
        XInStr = True
    Else
        For i = 0 To UBound(t)
            If InStr(s, t(i)) Then
                XInStr = True
                Exit For
            End If
        Next
    End If

End Function

'   機 能  :   拡張文字列置換
'   書 式  :   XReplace(s, ,t ,[u()])
'   返り値  :   文字列の検索文字列を置換文字列に置き換えた文字列
'   引 数  :   s   -   文字列
'               t   -   置換文字列
'   説 明  :   文字列 s に含まれている文字列 u(n) を文字列 t に置き換える

Public Function XReplace(s, t, ParamArray u()) As String

    Dim i               As Long         '   繰り返し変数
   
    XReplace = s
   
    If UBound(u) < 0 Then
        Exit Function
    Else
        For i = 0 To UBound(u)
            XReplace = Replace(XReplace, u(i), t)
        Next
    End If

End Function

XInstrは返り値が文字位置ではないこと、
XReplaceは引数の順序がReplaceと異なることに注意。

コメント

このブログの人気の投稿

文字列数式評価(5)~各項の和

文字列数式評価(1)