有効な浮動小数点数の確認

有効な浮動小数点数の確認

次のことをやりたいです: インペリアルまたはメートル法の単位に設定できるレポートを生成しています。すべての値は元々メートル法の単位なので、インペリアル単位の場合はすべての値を変換する必要があります。値が該当しない場合は、一部の値を N/A またはその他の文字列値にすることができます。ドキュメントは自動的に生成されます。変換には fp パッケージを使用していますが、入力のチェックが課題です。fp パッケージ (および pgfmath) は、数値以外の値で計算しようとすると、当然エラーになります。これが現在使用しているものです (整数入力でのみ機能します)

% Convert meters to inches
\newcommand{\convertmtoin}[2]
{
    \if!\ifnum9<1#1!\else_\fi   
    \FPeval{val}{#1*39.3700787} \FPround{\val}{\val}{#2}
    \else
    \def\val{#1}
    \fi
}

pgfmathを使用すると、次のようなことができます。

\newcommand{\convertmtoin}[2]
{
    \pgfmathfloatparsenumber{#1}
    \pgfmathfloatifflags{\pgfmathresult}{3}{\FPeval{val}{#1*39.3700787} \FPround{\val}{\val}{#2}}{\def\val{#1}} 
}

しかし、pgfmathfloatparsenumberへの誤った入力の場合にNaNを出力するようにpgfmathのエラーハンドラを設定することはできません。

\pgfkeys{/pgf/fpu/handlers/invalid number={??}{??}}

ご協力いただきありがとうございます!

答え1

\IfDecimalからご利用いただくこともできますそのxstring包み:

ここに画像の説明を入力してください

コード:

\documentclass{article}
\usepackage{xstring}

\newcommand*{\CheckIfNumerical}[1]{%
    \IfDecimal{#1}{%
        ``#1" is a number.%
    }{%
        ``#1" is NOT a number.%
    }%
}%


\begin{document}
\par\CheckIfNumerical{7}
\par\CheckIfNumerical{3.14}
\par\CheckIfNumerical{NaN}
\par\CheckIfNumerical{7. 0}
\par\CheckIfNumerical{7.0X09}
\end{document}

答え2

ネガティブな要素を処理できるように更新されました。

を呼び出すと、\testreal文字列内のすべてのバイトをチェックする再帰ループが設定されます。

まず、先頭の負数がある場合はそれを削除します。これは、文字列の残りの部分が有効な実数であるかどうかには影響しないためです。

残っているものについては、次のように処理が続行されます。文字列内に数字も小数点もまだ見つかっていないことに注意してください。ただし、有効な実数であると想定します。

連続する各バイトを調べて、小数点以外の数字が見つかると、テストは「失敗」状態に切り替わります。文字列内に小数点が 2 つ見つかった場合も、テストは失敗します。ただし、これらのテストの両方に合格した場合でも、テストに合格するには少なくとも 1 つの数字が見つかる必要があります。

\documentclass[]{article}

\def\testreal#1{\def\founddigit{F}\def\itsanumber{T}\def\fndpt{F}%
  \edef\tmp{\testleadneg#1\relax}%
  \expandafter\testrealhelper\tmp\relax%
  \if T\founddigit\itsanumber\else F\fi}

\def\testrealhelper#1#2\relax{%
\if.#1\if T\fndpt\def\itsanumber{F}\else\def\fndpt{T}\fi\else
\if1#1\FD\else
\if2#1\FD\else
\if3#1\FD\else
\if4#1\FD\else
\if5#1\FD\else
\if6#1\FD\else
\if7#1\FD\else
\if8#1\FD\else
\if9#1\FD\else
\if0#1\FD\else\def\itsanumber{F}%
\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi\fi
\if\relax#2\else\testrealhelper#2\relax\fi}

\def\testleadneg#1#2\relax{\if-#1#2\else#1#2\fi}

\def\FD{\def\founddigit{T}}
\begin{document}
\testreal{just}    \testreal{-just}

\testreal{123John} \testreal{-123John}

\testreal{324.56}  \testreal{-324.56}

\testreal{.}       \testreal{-.}

\testreal{23.4.56} \testreal{-23.4.56}

\testreal{346}     \testreal{-346}
\end{document} 

ここに画像の説明を入力してください

答え3

datatool引数が数値かどうかをテストするための条件を提供します。

ここに画像の説明を入力してください

\documentclass{article}
\usepackage{datatool}% http://ctan.org/pkg/datatool
\newcommand{\testreal}[1]{\ifthenelse{\DTLisnumerical{#1}}{T}{F}}
\begin{document}

\testreal{just}

\testreal{123John}

\testreal{324.56}

\testreal{.}

\testreal{23.4.56}

\testreal{346}
\end{document}

\DTLisnumericalと があります\DTLifnumerical。セクションを参照してください。2.2 ifthen条件文(p 16)のdatatoolユーザーガイド

答え4

あなたの意図がよく分かりませんでしたが、PGF ソリューションを考案するための簡単な例を以下に示します。

\documentclass[]{article}
\usepackage{pgf}
\usepgflibrary{fpu}

\pgfmathdeclarefunction{m2in}{1}{%
\begingroup
\pgfkeys{/pgf/fpu}
\pgfmathfloatparsenumber{#1}
\pgfmathfloatifflags{\pgfmathresult}{3}{%True Not a number
    \def\pgfmathresult{3Y0.0e0]}%
    \pgfmathfloattofixed{\pgfmathresult}%
    }{% False it is a number including inf
    \pgfmathfloatparsenumber{#1}%
    \pgfmathfloatmultiplyfixed{\pgfmathresult}{39.3700787}%
    \pgfmathfloattofixed{\pgfmathresult}%
    }
    \pgfmathsmuggle\pgfmathresult%
\endgroup
}%

\pgfkeys{/pgf/fpu/handlers/invalid number/.code={%
  \pgfmathfloatparsenumber{3Y0.0e0]}%
  }
}

\begin{document}
\pgfmathfloatparsenumber{435...}% NaN
    \pgfmathprintnumber[fixed]{\pgfmathresult}
    
\pgfmathfloatparsenumber{la la laa}% NaN
    \pgfmathprintnumber[fixed]{\pgfmathresult}

\pgfmathparse{m2in(1.000)}\pgfmathprintnumber[fixed,precision=5]\pgfmathresult

\pgfmathparse{m2in(4..4)}\pgfmathresult
\end{document}

これにより、

非N

非N

39.37007

ナン

関連情報