• ベストアンサー
※ ChatGPTを利用し、要約された質問です(原文:ユーザー定義関数について質問します。2)

ユーザー定義関数についての質問とは?

このQ&Aのポイント
  • 数式の上付き文字を指数として認識できるユーザー定義関数がありますが、一部の条件下で不具合が発生しています。
  • 上付き文字より右に式が続くと指数扱いにならず、誤った計算結果が表示されてしまう場合があります。
  • 改善策を教えていただけると助かります。

質問者が選んだベストアンサー

  • ベストアンサー
  • Wendy02
  • ベストアンサー率57% (3570/6232)
回答No.5

これは、直接の回答ではありません。 一応、このユーザー定義関数の問題になった部分--二つの上付き文字を算出できない--場合の理由を、記録として残しておきます。 [累乗は、本来は、書式上付き文字] この場合の、Font のSuperscript は、 F =False, T = True, N =Null 2×2^2        NNNT 2^1×2        NNFF   2×2^2×2      NNNNFF 2×2^2×3^2     NNNNNNT  × 2^2×2^2×3^3    NNNNNNNT  × 二つある場合は取得できません。(一体、どことどこに上付き文字があるのかは、これでは分かりません)少なくとも、この方法では、無理だということが分かります。 '検査用マクロ Sub TEST_Superscript() Dim rng As Range Dim i As Long Dim buf As Variant Dim k As String Set rng = ActiveCell For i = 1 To Len(rng.Value)  If IsNull(rng.Characters(i).Font.Superscript) Then   buf = "N" 'Null  Else  'True / False   buf = Left(CStr(rng.Characters(i).Font.Superscript), 1)  End If   k = k & buf   buf = "" Next i   rng.Offset(, 1).Value = k End Sub

その他の回答 (4)

  • Wendy02
  • ベストアンサー率57% (3570/6232)
回答No.4

こんにちは。 >指数が2回出る場合、エラー表示せず、誤計算するようです。 エラーを出すようにはしたつもりだったのですが、エラーが出ないようです。 それは、最初にも書いたように、現在の方法では、どんなにやっても、事実上不可能です。Rangeオブジェクトのフォントプロパティの中の上付き文字の判定は、一回限りだと思います。 少なくとも、私の今のVBAの能力では、無理だと思います。私以外の人で出来る方がいらっしゃるかもしれませんが、それは、また新たにお願いします。これ以外の問題でありましたら、直すことは可能です。

noname#192339
質問者

お礼

返答ありがとうございます。 検証のためしばらくこのままで使わせてもらいます。 もし何かあれば報告します。その時はまた見てください。 ありがとうございました。

  • Wendy02
  • ベストアンサー率57% (3570/6232)
回答No.3

こんにちは。 サブルーチンはそのままです。T2C側だけを入れ替えてみてください。 これで、しばらく様子をみていただけますか? Public Function T2C(セル As Variant, Optional pwrs As Integer = 1) As Variant 'goo_no.2848879 20.03.07_v.0.4 Dim strArg As String Dim ssflg As Boolean Dim rng As Range Dim TOp As Variant Dim Op As Variant Dim i As Integer Dim j As Integer Dim buf As String Dim k As Integer 'pwrs = 1 '累乗の桁 '√は、必ず、最後にしてください。 '本来は、+,-は、文字列を半角にしてしまうので不要です。 Const TXTOPERAND As String = "[,],{,},+,-,×,÷,π,√" Const OPERAND As String = "(,),(,),+,-,*,/,PI(),SQRT" TOp = Split(TXTOPERAND, ",") Op = Split(OPERAND, ",") 'Altered Two Byte Argument to One Byte Variable Set rng = セル If StrComp(TypeName(rng), "RANGE", vbTextCompare) <> 0 Then Exit Function If VarType(rng) = vbDouble Then T2C = rng.Value: Exit Function 'SuperScript Checking  If Not rng.Characters(1).Font.Superscript = Null Then     For i = 1 To Len(rng.Value)       If rng.Characters(i).Font.Superscript = True And ssflg = False Then         strArg = strArg & "^" & Mid$(rng.Value, i, 1)         ssflg = True       Else         strArg = strArg & Mid$(rng.Value, i, 1)       End If     Next i   Else     For j = 1 To Len(rng.Value)       If rng.Characters(j).Font.Superscript = False And ssflg = False Then         strArg = strArg & Mid$(rng.Value, j, 1)         If buf <> "" Then ssflg = True       ElseIf IsNull(rng.Characters(j).Font.Superscript) And ssflg = False Then         buf = buf & Mid$(rng.Value, j, 1)       ElseIf rng.Characters(j).Font.Superscript Then         If j = Len(rng.Value) - (pwrs - 1) Then           strArg = buf & "^" & Mid$(rng.Value, j - (pwrs - 1), pwrs)         Else         T2C = "double power N/A": Exit Function         End If       End If       If ssflg Then         '累乗処理         buf = Mid$(buf, 1, Len(buf) - pwrs) & "^" & Right(buf, pwrs)         strArg = buf & strArg         buf = ""         ssflg = False       End If     Next j   End If '半角へ変換 strArg = StrConv(strArg, vbNarrow) For k = LBound(TOp) To UBound(TOp)   If TOp(k) = "√" Then     If InStr(strArg, "√") > 0 Then       '√を変換するための関数       strArg = RootExchange(strArg)     End If   Else     strArg = Replace(strArg, TOp(k), Op(k))   End If Next k T2C = Application.Evaluate(strArg) End Function

noname#192339
質問者

お礼

回答ありがとうございます。 指数は前にあっても後ろにあっても正常になりました。 ただ、指数が2回出る場合、エラー表示せず、誤計算するようです。 これ以上はご迷惑がかかるので、今はこれで使用してみます。 また時間があればお願いいたします。

  • Wendy02
  • ベストアンサー率57% (3570/6232)
回答No.2

こんにちは。 作り直してみました。 そこで、指数に関しては、基本的には、1桁を用いる場合のみになります。 [^2は、書式で設定されているものとします] 3^2×2    =T2C(A1) 3^10×2   =T2C(A1,2)   'この場合は、引数を入れると解は出ます。 ただし、指数が、二つになると、 2^2×2+2^3  =T2C(A1)  で行うと、エラーを出すようにしてあります。最初の「上付き文字」側が、今の方法からでは、1度目の「上付き文字」を認識する方法が見つかりません。 今までのものに、入れ替えてください。 '----------------------------------------------------------- Public Function T2C(セル As Variant, Optional pwrs As Integer = 1) As Variant 'goo_no.2848879 20.03.07_v.0.3 Dim strArg As String Dim ssflg As Boolean Dim rng As Range Dim TOp As Variant Dim Op As Variant Dim i As Integer Dim j As Integer Dim buf As String Dim k As Integer 'pwrs = 1 '累乗の桁 '√は、必ず、最後にしてください。 '本来は、+,-は、文字列を半角にしてしまうので不要です。 Const TXTOPERAND As String = "[,],{,},+,-,×,÷,π,√" Const OPERAND As String = "(,),(,),+,-,*,/,PI(),SQRT" TOp = Split(TXTOPERAND, ",") Op = Split(OPERAND, ",") 'Altered Two Byte Argument to One Byte Variable Set rng = セル If StrComp(TypeName(rng), "RANGE", vbTextCompare) <> 0 Then Exit Function If VarType(rng) = vbDouble Then T2C = rng.Value: Exit Function 'SuperScript Checking  If Not rng.Characters(1).Font.Superscript = Null Then     For i = 1 To Len(rng.Value)       If rng.Characters(i).Font.Superscript = True And ssflg = False Then         strArg = strArg & "^" & Mid$(rng.Value, i, 1)         ssflg = True       Else         strArg = strArg & Mid$(rng.Value, i, 1)       End If     Next i   Else     For j = 1 To Len(rng.Value)       If rng.Characters(j).Font.Superscript = False And ssflg = False Then         strArg = strArg & Mid$(rng.Value, j, 1)         If buf <> "" Then ssflg = True       ElseIf IsNull(rng.Characters(j).Font.Superscript) And ssflg = False Then         buf = buf & Mid$(rng.Value, j, 1)       ElseIf rng.Characters(j).Font.Superscript Then         T2C = "double power N/A": Exit Function       End If       If ssflg Then         '累乗処理         buf = Mid$(buf, 1, Len(buf) - pwrs) & "^" & Right(buf, pwrs)         strArg = buf & strArg         buf = ""         ssflg = False       End If     Next j   End If '半角へ変換 strArg = StrConv(strArg, vbNarrow) For k = LBound(TOp) To UBound(TOp)   If TOp(k) = "√" Then     If InStr(strArg, "√") > 0 Then       '√を変換するための関数       strArg = RootExchange(strArg)     End If   Else     strArg = Replace(strArg, TOp(k), Op(k))   End If Next k T2C = Application.Evaluate(strArg) End Function Private Function RootExchange(strArg As String) As String 'ルートを変換するための関数   Dim flg As Boolean   Dim buf As String   Dim i As Integer   If Len(strArg) - Len(Replace(strArg, "√", "")) > 1 Then     For i = 1 To Len(strArg)       If Mid(strArg, i, 1) = "√" And flg = False Then         buf = buf & "SQRT("         flg = True       ElseIf Mid(strArg, i, 1) Like "[.0-9]" Then         buf = buf & Mid(strArg, i, 1)       ElseIf Mid(strArg, i, 1) = "√" Then         buf = buf & ")SQRT"         flg = True       Else         If flg Then             buf = buf & ")" & Mid(strArg, i, 1)             flg = False         Else             buf = buf & Mid(strArg, i, 1)                End If            End If     Next i    Else     buf = Replace(strArg, "√", "SQRT(")     flg = True   End If   If flg = True Then     RootExchange = buf & ")"   Else     RootExchange = buf   End If End Function

noname#192339
質問者

お礼

Wendy02さん ありがとうございます。 早速使わせてもらいました。 今度は逆の現象が起こります。 3^2×2 → OK 2×3^2 → double power N/A です。 自力ではも不可能となってます。(^^ゞ またよろしくお願いします。

  • Wendy02
  • ベストアンサー率57% (3570/6232)
回答No.1

こんにちは。Wendy02です。 現象は確認したのですが、なぜ、そんなことが起こるのか原因が良く分からないでいます。ユーザー定義関数の動きを、VBE のローカルウィンドウで確認してみてみましたら、VBA自身が、3^2×2(実際は^2は、[^]がなく書式だけ) の 2の部分の「上付き文字」が、認識できずに「抜け=null」が起きています。 もう一度、最初から、調べないといけないようです。すみませんが、単純にコードのミスとも言えないので、しばらくお時間いただけないでしょうか?

関連するQ&A