Ich möchte ein Makro zum Entfernen der Null aus der Dezimalstelle schreiben, z. B. 2.0
in 2
eine Zahl umwandeln.
dies ist mein Versuch, eine Null zu entfernen, aber es funktioniert nicht und erzeugt einen Fehler:
\documentclass[borders=2cm]{standalone}
\usepackage{tikz}
\newcommand{\isinteger}[1]{\pgfmathtruncatemacro{\intvar}{#1}
\def\newx{\pgfmathparse{10*(\intvar-#1)}\pgfmathresult}
\ifnum\newx=0
\intvar
\else
#1
\fi}
\begin{document}
\isinteger{1.5}
\end{document}
Fehler:
Missing number, treated as zero. \isinteger{1.5}
Missing = inserted for \ifnum. \isinteger{1.5}
Missing number, treated as zero. \isinteger{1.5}
Irgendeine Idee?
Antwort1
Wenn Sie nur eine Ganzzahl als Ganzzahl und eine Nicht-Ganzzahl als Nicht-Ganzzahl ausgeben möchten und da Sie bereitspgfmath, empfehle ich die Verwendung von \pgfmathprintnumber
. Es wird ausführlich in Kapitel 98 desTikZHandbuch, aber das Folgende scheint zu funktionieren, was Sie wollen:
\documentclass{article}
\usepackage{tikz}
\newcommand{\isinteger}[1]{\pgfmathprintnumber[int detect,fixed]{#1}}
\begin{document}
\isinteger{1.5}
\isinteger{1.0}
\end{document}
Dies druckt 1.5
bzw. 1
.
Eine weitere Möglichkeit ist die Verwendung \num
vonAbonnieren:
\documentclass{article}
\usepackage{siunitx}
\newcommand{\isinteger}[1]{\num[zero-decimal-to-integer=true]{#1}}
\begin{document}
\isinteger{1.5}
\isinteger{1.0}
\end{document}
Antwort2
Antwort3
Eine Variante von Davids Antwort, wenn das Ziel nur darin besteht, keine nachstehenden Nullen zu drucken:
\documentclass{article}
\usepackage{xfp}
\begin{document}
\fpeval{1}
\fpeval{1.0}
\fpeval{1.5}
\fpeval{14/5-4/5}
\fpeval{round(4*pi*3.4^3/3,0)} % round to integer
\end{document}
Beachten Sie, dass das fp
Modul expl3
(das hier verwendet wird) viel genauer ist als die PGF-Gleitkomma-Dienstprogramme.
Antwort4
Ich kann eine erweiterbare Routine zum „Normalisieren“ von Zahlen anbieten \normalizenumber
.
Um zu erklären, wie \normalizenumber
das funktioniert, möchte ich – zusätzlich zu dem, was in der TeX-Grammatik im TeXBook in Backus/Naur-Notation definiert ist – eine Menge definieren⟨Dezimaltrennzeichen⟩:
⟨Dezimaltrennzeichen⟩→. 12|, 12
Die Syntax \normalizenumber
lautet:
\normalizenumber⟨undelimited argument⟩
Fall 1:
Die gebildeten Token ⟨undelimited argument⟩
entsprechen dem Muster
⟨optionale Zeichen⟩⟨Ganzzahlige Konstante⟩⟨ein optionales Leerzeichen⟩
Im Fall 1
- ⟨optionale Zeichen⟩werden wie nachfolgend beschrieben konvertiert und ausgeliefert.
- ⟨Ganzzahlige Konstante⟩Es wird eine Ziffer zurückgegeben, bei der alle führenden Nullen entfernt wurden.
Falls das Entfernen aller führenden Nullen ein leeres Ergebnis ergibt, wird eine einzelne Ziffer zurückgegeben.012
- ⟨ein optionales Leerzeichen⟩ist entfernt.
Fall 2:
Die gebildeten Token ⟨undelimited argument⟩
entsprechen dem Muster
⟨optionale Zeichen⟩⟨Ganzzahlige Konstante⟩⟨Dezimaltrennzeichen⟩⟨Ganzzahlige Konstante⟩⟨ein optionales Leerzeichen⟩
Im Fall 2
- ⟨optionale Zeichen⟩werden wie nachfolgend beschrieben konvertiert und ausgeliefert.
- Die erste/linke⟨Ganzzahlige Konstante⟩wird mit allen führenden Nullen entfernt zurückgegeben.
Falls das Entfernen aller führenden Nullen leer bleibt, wird eine einzelne Ziffer zurückgegeben.012
- Wenn alle nachfolgenden Nullen aus der zweiten/rechten⟨Ganzzahlige Konstante⟩keine Leere hervorbringt, dann⟨Dezimaltrennzeichen⟩wird geliefert.
- Die zweite/rechte⟨Ganzzahlige Konstante⟩wird ohne die Entfernung aller abschließenden Nullen geliefert.
- ⟨ein optionales Leerzeichen⟩ist entfernt.
In allen anderen FällenDie Token, die die bilden, ⟨undelimited argument⟩
werden unverändert übergeben.
Geschweifte Klammern, die die begrenzen, ⟨undelimited argument⟩
werden entfernt.
In jedem FallDurch die \romannumeral0
-Expansion wird das Ergebnis nach zwei Expansionsschritten bzw. durch zweimaliges "Schlagen" \normalizenumber
mit geliefert \expandafter
.
Die eben genannten Dinge implizieren, dass z. B. unverändert \normalizenumber{1.}
zurückkehrt 1.
, weil die⟨unbegrenztes Argument⟩ 1.
weder entspricht das Muster, das für Fall 1 beschrieben wurde, noch entspricht das Muster, das für Fall 2 beschrieben wurde. \normalizenumber{1.000}
ergibt 1
— die⟨unbegrenztes Argument⟩ 1.000
weist das für Fall 2 beschriebene Muster auf.
Umwandlung von⟨optionale Zeichen⟩
Falls⟨optionale Zeichen⟩eine nicht-negative Zahl bezeichnen, wird für sie überhaupt kein Token zurückgegeben.
Falls⟨optionale Zeichen⟩eine negative Zahl bezeichnen, wird dafür ein einzelnes explizites Zeichentoken zurückgegeben. Wenn der absolute Wert der zu normalisierenden Zahl 0 ist, erhalten Sie kein Vorzeichen – Sie erhalten nicht, sondern Sie erhalten .-12
-0
0
Erweiterung \normalizenumber
von⟨unbegrenztes Argument⟩
\normalizenumber
in einer Endrekursionsschleife untersucht er sein Argument tokenweise: Wenn das erste Token des⟨unbegrenztes Argument⟩bedeutet nicht, dass die⟨unbegrenztes Argument⟩weder dem Muster von Fall 1 noch dem Muster von Fall 2 entspricht, dann wird es aus dem⟨unbegrenztes Argument⟩für die nächste Iteration und in der nächsten Iteration \normalizenumber
wird das erste Token des verbleibenden⟨unbegrenztes Argument⟩.
Es gibt einen \if
-Schalter \ifnormalizenumberexpandarg
.
Wenn Sie sagen \normalizenumberexpandargfalse
, dann \normalizenumber
werden bei der Prüfung keine erweiterbaren Token erweitert und das Auftreten eines erweiterbaren Tokens bedeutet, dass die⟨unbegrenztes Argument⟩entspricht weder dem für Fall 1 beschriebenen Muster noch dem für Fall 2 beschriebenen Muster.
Wenn Sie sagen \normalizenumberexpandargtrue
, dann in jeder Iteration feststellen, dass das erste Token der⟨unbegrenztes Argument⟩ist erweiterbar, löst das "Treffer" aus \expandafter
und untersucht in der nächsten Iteration das Ergebnis. Das Erweitern des ersten Tokens des⟨unbegrenztes Argument⟩kann sich auf nachfolgende Token des⟨unbegrenztes Argument⟩.
Verwenden Sie es \normalizenumberexpandargtrue
mit Vorsicht und einer gewissen Portion Misstrauen:
Wenn das erste Token ein unbalanced \else
oder \fi
oder ein unbalanced ist \csname
, können Sie alle möglichen seltsamen Fehlermeldungen erhalten. Wenn das erste Token so definiert ist, dass es Dinge auslöst, die Token jenseits der schließenden Klammer des⟨unbegrenztes Argument⟩, dann kann der Programmablauf unvorhersehbar werden. Wenn das erste Token so definiert ist, dass es sich selbst liefert, kann es sein, dass Sie in einer Endlosschleife landen.
\errorcontextlines=10000
\documentclass{article}
\makeatletter
%%=============================================================================
%% Paraphernalia:
%% \UD@firstoftwo, \UD@secondoftwo, \UD@Exchange, \UD@Removespace
%% \UD@CheckWhetherNull, \UD@CheckWhetherLeadingSpace, \UD@ExtractFirstArg
%%=============================================================================
\newcommand\UD@firstoftwo[2]{#1}%
\newcommand\UD@secondoftwo[2]{#2}%
\newcommand\UD@Exchange[2]{#2#1}%
\@ifdefinable\UD@Removespace{\UD@Exchange{ }{\def\UD@Removespace}{}}%
%%-----------------------------------------------------------------------------
%% Check whether argument is empty:
%%.............................................................................
%% \UD@CheckWhetherNull{<Argument which is to be checked>}%
%% {<Tokens to be delivered in case that argument
%% which is to be checked is empty>}%
%% {<Tokens to be delivered in case that argument
%% which is to be checked is not empty>}%
%%
%% The gist of this macro comes from Robert R. Schneck's \ifempty-macro:
%% <https://groups.google.com/forum/#!original/comp.text.tex/kuOEIQIrElc/lUg37FmhA74J>
\newcommand\UD@CheckWhetherNull[1]{%
\romannumeral0\expandafter\UD@secondoftwo\string{\expandafter
\UD@secondoftwo\expandafter{\expandafter{\string#1}\expandafter
\UD@secondoftwo\string}\expandafter\UD@firstoftwo\expandafter{\expandafter
\UD@secondoftwo\string}\expandafter\expandafter\UD@firstoftwo{ }{}%
\UD@secondoftwo}{\expandafter\expandafter\UD@firstoftwo{ }{}\UD@firstoftwo}%
}%
%%-----------------------------------------------------------------------------
%% Check whether argument's first token is a catcode-1-character
%%.............................................................................
%% \UD@CheckWhetherBrace{<Argument which is to be checked>}%
%% {<Tokens to be delivered in case that argument
%% which is to be checked has leading
%% catcode-1-token>}%
%% {<Tokens to be delivered in case that argument
%% which is to be checked has no leading
%% catcode-1-token>}%
\newcommand\UD@CheckWhetherBrace[1]{%
\romannumeral0\expandafter\UD@secondoftwo\expandafter{\expandafter{%
\string#1.}\expandafter\UD@firstoftwo\expandafter{\expandafter
\UD@secondoftwo\string}\expandafter\expandafter\UD@firstoftwo{ }{}%
\UD@firstoftwo}{\expandafter\expandafter\UD@firstoftwo{ }{}\UD@secondoftwo}%
}%
%%-----------------------------------------------------------------------------
%% Check whether brace-balanced argument starts with a space-token
%%.............................................................................
%% \UD@CheckWhetherLeadingSpace{<Argument which is to be checked>}%
%% {<Tokens to be delivered in case <argument
%% which is to be checked>'s 1st token is a
%% space-token>}%
%% {<Tokens to be delivered in case <argument
%% which is to be checked>'s 1st token is not
%% a space-token>}%
\newcommand\UD@CheckWhetherLeadingSpace[1]{%
\romannumeral0\UD@CheckWhetherNull{#1}%
{\expandafter\expandafter\UD@firstoftwo{ }{}\UD@secondoftwo}%
{\expandafter\UD@secondoftwo\string{\UD@CheckWhetherLeadingSpaceB.#1 }{}}%
}%
\newcommand\UD@CheckWhetherLeadingSpaceB{}%
\long\def\UD@CheckWhetherLeadingSpaceB#1 {%
\expandafter\UD@CheckWhetherNull\expandafter{\UD@firstoftwo{}#1}%
{\UD@Exchange{\UD@firstoftwo}}{\UD@Exchange{\UD@secondoftwo}}%
{\UD@Exchange{ }{\expandafter\expandafter\expandafter\expandafter
\expandafter\expandafter\expandafter}\expandafter\expandafter
\expandafter}\expandafter\UD@secondoftwo\expandafter{\string}%
}%
%%=============================================================================
%% Extract K-th inner undelimited argument:
%%
%% \UD@ExtractKthArg{<integer K>}{<list of undelimited args>}
%%
%% In case there is no K-th argument in <list of indelimited args> :
%% Does not deliver any token.
%% In case there is a K-th argument in <list of indelimited args> :
%% Does deliver that K-th argument with one level of braces removed.
%%
%% Examples:
%%
%% \UD@ExtractKthArg{0}{ABCDE} yields: <nothing>
%%
%% \UD@ExtractKthArg{3}{ABCDE} yields: C
%%
%% \UD@ExtractKthArg{3}{AB{CD}E} yields: CD
%%
%% \UD@ExtractKthArg{4}{{001}{002}{003}{004}{005}} yields: 004
%%
%% \UD@ExtractKthArg{6}{{001}{002}{003}} yields: <nothing>
%%
%%=============================================================================
\newcommand\UD@ExtractKthArg[1]{%
\romannumeral0%
% #1: <integer number K>
\expandafter\UD@ExtractKthArgCheck
\expandafter{\romannumeral\number\number#1 000}%
}%
\newcommand\UD@ExtractKthArgCheck[2]{%
\UD@CheckWhetherNull{#1}{ }{%
\expandafter\UD@ExtractKthArgLoop\expandafter{\UD@firstoftwo{}#1}{#2}%
}%
}%
\newcommand\UD@ExtractKthArgLoop[2]{%
\expandafter\UD@CheckWhetherNull\expandafter{\UD@firstoftwo#2{}.}{ }{%
\UD@CheckWhetherNull{#1}{%
\UD@ExtractFirstArgLoop{#2UD@SelDOm}%
}{%
\expandafter\UD@Exchange\expandafter{\expandafter{\UD@firstoftwo{}#2}}%
{\expandafter\UD@ExtractKthArgLoop\expandafter{\UD@firstoftwo{}#1}}%
}%
}%
}%
\@ifdefinable\UD@RemoveTillUD@SelDOm{%
\long\def\UD@RemoveTillUD@SelDOm#1#2UD@SelDOm{{#1}}%
}%
\newcommand\UD@ExtractFirstArgLoop[1]{%
\expandafter\UD@CheckWhetherNull\expandafter{\UD@firstoftwo{}#1}%
{\UD@firstoftwo{\expandafter}{} \UD@secondoftwo{}#1}%
{\expandafter\UD@ExtractFirstArgLoop\expandafter{\UD@RemoveTillUD@SelDOm#1}}%
}%
%%=============================================================================
%% Fork if argument, which must be a single token, is
%% 0/1/2/3/4/5/6/7/8/9/+/-/./,/<space token>/<expandable token>/<something else>
%% (total: 17 cases)
%%-----------------------------------------------------------------------------
\@ifdefinable\UD@GobbleToExclam{\long\def\UD@GobbleToExclam#1!{}}%
%%-----------------------------------------------------------------------------
\@ifdefinable\UD@normalizenumberfork{%
\long\def\UD@normalizenumberfork#1!0!1!2!3!4!5!6!7!8!9!+!-!,!.!#2#3!!!!{#2}%
}%
\newcommand\UD@normalizenumberloopfork[1]{%
\expandafter\UD@CheckWhetherNull\expandafter{\UD@GobbleToExclam#1!}{%
\UD@normalizenumberfork
!#1!1!2!3!4!5!6!7!8!9!+!-!,!.!{1}% <digit> 0_12
!0!#1!2!3!4!5!6!7!8!9!+!-!,!.!{2}% <digit> 1_12
!0!1!#1!3!4!5!6!7!8!9!+!-!,!.!{3}% <digit> 2_12
!0!1!2!#1!4!5!6!7!8!9!+!-!,!.!{4}% <digit> 3_12
!0!1!2!3!#1!5!6!7!8!9!+!-!,!.!{5}% <digit> 4_12
!0!1!2!3!4!#1!6!7!8!9!+!-!,!.!{6}% <digit> 5_12
!0!1!2!3!4!5!#1!7!8!9!+!-!,!.!{7}% <digit> 6_12
!0!1!2!3!4!5!6!#1!8!9!+!-!,!.!{8}% <digit> 7_12
!0!1!2!3!4!5!6!7!#1!9!+!-!,!.!{9}% <digit> 8_12
!0!1!2!3!4!5!6!7!8!#1!+!-!,!.!{10}% <digit> 9_12
!0!1!2!3!4!5!6!7!8!9!#1!-!,!.!{11}% <plus or minus> +_12
!0!1!2!3!4!5!6!7!8!9!+!#1!,!.!{12}% <plus or minus> -_12
!0!1!2!3!4!5!6!7!8!9!+!-!#1!.!{13}% <decimal constant> ,_12
!0!1!2!3!4!5!6!7!8!9!+!-!,!#1!{14}% <decimal constant> ._12
!0!1!2!3!4!5!6!7!8!9!+!-!,!.!{%
\ifcat\noexpand#1 \expandafter\UD@firstoftwo\else\expandafter\UD@secondoftwo\fi
{15}% <space token> differing from explicit character token of catcode 10
% and charcode 32; removable as undelimited argument
{%
\expandafter\ifx\noexpand#1#1%
\expandafter\UD@firstoftwo\else\expandafter\UD@secondoftwo\fi
{18}% something else which is not allowed
{17}% expandable token
}%
}%
!!!!%
}{18}% Case: #1 contains !_12 , therefore is something else which is not
% allowed
}%
%%=============================================================================
%% \normalizenumber{<argument>}
%%-----------------------------------------------------------------------------
\newcommand\normalizenumber[1]{%
\romannumeral0%
\normalizenumberloop{#1}{}{}{#1}{\UD@firstoftwo}{}{\UD@firstoftwo}{}%
}%
\newif\ifnormalizenumberexpandarg\normalizenumberexpandargfalse
\newcommand\normalizenumberloop[8]{%
% #1 - argument to iterate
% #2 - leading zero if found
% #3 - optional minus sign
% #4 - argument untouched
% #5 - decimal separator not/already found - \UD@firstoftwo/\UD@secondoftwo
% #6 - zero-decimals collected so far
% #7 - sign-check on/off - \UD@firstoftwo/\UD@secondoftwo
% #8 - significant digits collected so far
\UD@CheckWhetherNull{#1}{%
\UD@CheckWhetherNull{#8}{\UD@CheckWhetherNull{#2}{ #4}{ #2}}{ #3#8}%
}{%
\UD@ExtractKthArg{%
%-------------------------------------------------------------------------
% \UD@ExtractKthArg's <integer K>:
%-------------------------------------------------------------------------
% Code for calculating \UD@ExtractKthArg's <integer K>
\UD@CheckWhetherBrace{#1}{%
18% argument to iterate's 1st token has catcode 1, therefore is not
% allowed.
}{%
\UD@CheckWhetherLeadingSpace{#1}{%
16% explicit character token of catcode 10 and charcode 32; not
% removable as undelimited argument
}{%
\expandafter\UD@normalizenumberloopfork
\expandafter{\romannumeral0\UD@ExtractFirstArgLoop{#1UD@SelDOm}}%
}%
}%
}{%
%-------------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>:
%-------------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 1st argument:
% \UD@ExtractKthArg's 1st argument yields the number 1, thus #1's
% 1st token is <digit> 0_12
{%
#5{%
\UD@CheckWhetherNull{#8}{%
\UD@firstoftwo{%
\expandafter\normalizenumberloop\expandafter{\UD@firstoftwo{}#1}{0}{#3}{#4}{#5}{}{\UD@secondoftwo}{#8}%
}%
}{\UD@Exchange{{#80}}}%
}{%
\UD@firstoftwo{%
\expandafter\normalizenumberloop
\expandafter{\UD@firstoftwo{}#1}{#2}%
{#3}{#4}{#5}{#60}{\UD@secondoftwo}{#8}%
}%
}%
}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 2nd argument:
% \UD@ExtractKthArg's 1st argument yields the number 2, thus #1's
% 1st token is <digit> 1_12
{\UD@Exchange{{#8#61}}}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 3rd argument:
% \UD@ExtractKthArg's 1st argument yields the number 3, thus #1's
% 1st token is <digit> 2_12
{\UD@Exchange{{#8#62}}}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 4th argument:
% \UD@ExtractKthArg's 1st argument yields the number 4, thus #1's
% 1st token is <digit> 3_12
{\UD@Exchange{{#8#63}}}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 5th argument:
% \UD@ExtractKthArg's 1st argument yields the number 5, thus #1's
% 1st token is <digit> 4_12
{\UD@Exchange{{#8#64}}}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 6th argument:
% \UD@ExtractKthArg's 1st argument yields the number 6, thus #1's
% 1st token is <digit> 5_12
{\UD@Exchange{{#8#65}}}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 7th argument:
% \UD@ExtractKthArg's 1st argument yields the number 7, thus #1's
% 1st token is <digit> 6_12
{\UD@Exchange{{#8#66}}}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 8th argument:
% \UD@ExtractKthArg's 1st argument yields the number 8, thus #1's
% 1st token is <digit> 7_12
{\UD@Exchange{{#8#67}}}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 9th argument:
% \UD@ExtractKthArg's 1st argument yields the number 9, thus #1's
% 1st token is <digit> 8_12
{\UD@Exchange{{#8#68}}}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 10th argument:
% \UD@ExtractKthArg's 1st argument yields the number 10, thus #1's
% 1st token is <digit> 9_12
{\UD@Exchange{{#8#69}}}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 11th argument:
% \UD@ExtractKthArg's 1st argument yields the number 11, thus #1's
% 1st token is <plus or minus> +_12
{%
\UD@firstoftwo{%
#7{%
\expandafter\UD@CheckWhetherNull
\expandafter{\UD@firstoftwo{}#1}{ #4}{%
\expandafter\normalizenumberloop
\expandafter{\UD@firstoftwo{}#1}{#2}{#3}{#4}{#5}{#6}{#7}{#8}%
}%
}{ #4}%
}%
}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 12th argument:
% \UD@ExtractKthArg's 1st argument yields the number 12, thus #1's
% 1st token is <plus or minus> -_12
{%
\UD@firstoftwo{%
#7{%
\expandafter\UD@CheckWhetherNull
\expandafter{\UD@firstoftwo{}#1}{ #4}{%
\UD@CheckWhetherNull{#3}{\UD@Exchange{{-}}}{\UD@Exchange{{}}}%
{\expandafter\normalizenumberloop\expandafter{\UD@firstoftwo{}#1}{#2}}%
{#4}{#5}{#6}{#7}{#8}%
}%
}{ #4}%
}%
}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 13th argument:
% \UD@ExtractKthArg's 1st argument yields the number 13, thus #1's
% 1st token is <decimal constant> ,_12
{%
\UD@firstoftwo{%
#5{%
\expandafter\UD@CheckWhetherNull
\expandafter{\UD@firstoftwo{}#1}{ #4}{%
\UD@CheckWhetherNull{#2#8}{ #4}{%
\UD@CheckWhetherNull{#8}{\UD@Exchange{{#2}}}{\UD@Exchange{{#8}}}%
{%
\expandafter\normalizenumberloop\expandafter{\UD@firstoftwo{}#1}%
{#2}{#3}{#4}{\UD@secondoftwo}{,}{\UD@secondoftwo}%
}%
}%
}%
}{ #4}%
}%
}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 14th argument:
% \UD@ExtractKthArg's 1st argument yields the number 14, thus #1's
% 1st token is <decimal constant> ._12
{%
\UD@firstoftwo{%
#5{%
\expandafter\UD@CheckWhetherNull
\expandafter{\UD@firstoftwo{}#1}{ #4}{%
\UD@CheckWhetherNull{#2#8}{ #4}{%
\UD@CheckWhetherNull{#8}{\UD@Exchange{{#2}}}{\UD@Exchange{{#8}}}%
{%
\expandafter\normalizenumberloop\expandafter{\UD@firstoftwo{}#1}%
{#2}{#3}{#4}{\UD@secondoftwo}{.}{\UD@secondoftwo}%
}%
}%
}%
}{ #4}%
}%
}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 15th argument:
% \UD@ExtractKthArg's 1st argument yields the number 15, thus #1's
% 1st token is a <space token> differing from explicit character
% token of catcode 10 and charcode 32 and is removable as
% undelimited argument
{%
\UD@firstoftwo{%
#7{\UD@firstoftwo}{%
\expandafter\UD@CheckWhetherNull\expandafter{\UD@firstoftwo{}#1}%
}%
{%
\expandafter\normalizenumberloop
\expandafter{\UD@firstoftwo{}#1}{#2}{#3}{#4}{#5}{#6}{#7}{#8}%
}%
{ #4}%
}%
}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 16th argument:
% \UD@ExtractKthArg's 1st argument yields the number 16, thus #1's
% 1st token is a <space token>, more precisely an explicit
% character token of catcode 10 and charcode 32 and is not removable
% as undelimited argument
{%
\UD@firstoftwo{%
#7{\UD@firstoftwo}{%
\expandafter\UD@CheckWhetherNull\expandafter{\UD@Removespace#1}%
}%
{%
\expandafter\normalizenumberloop
\expandafter{\UD@Removespace#1}{#2}{#3}{#4}{#5}{#6}{#7}{#8}%
}%
{ #4}%
}%
}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 17th argument:
% \UD@ExtractKthArg's 1st argument yields the number 17, thus #1's
% 1st token is expandable.
{%
\UD@firstoftwo{%
\ifnormalizenumberexpandarg
\expandafter\UD@firstoftwo\else\expandafter\UD@secondoftwo\fi
{\expandafter\normalizenumberloop\expandafter{#1}{#2}{#3}{#4}{#5}{#6}{#7}{#8}}%
{ #4}%
}%
}%
%-----------------------------------------------------------------------
% \UD@ExtractKthArg's <list of undelimited args>'s 18th argument:
% \UD@ExtractKthArg's 1st argument yields the number 18, thus #1's
% 1st token is not allowed with numbers that can be normalized.
{%
\UD@firstoftwo{ #4}%
}%
%-------------------------------------------------------------------------
% End of \UD@ExtractKthArg's <list of undelimited args>.
%-------------------------------------------------------------------------
}%
{\expandafter\normalizenumberloop\expandafter{\UD@firstoftwo{}#1}%
{#2}{#3}{#4}{#5}{}{\UD@secondoftwo}%
}%
}%
}%
%%.............................................................................
\makeatother
% Test \normalizenumber by applying it inside the definition-text of \test:
\newcommand\Test[1]{%
\expandafter\expandafter\expandafter\def
\expandafter\expandafter\expandafter\test
\expandafter\expandafter\expandafter{#1}%
\texttt{(\meaning\test)}%
}%
\makeatletter\let\sptoken= \@sptoken\makeatother
\begin{document}
\null\kern-2cm
The following either comply the pattern described in case 1 or comply the pattern described in case 2:
01: \Test{\normalizenumber{-\sptoken\sptoken-\sptoken++\sptoken00000.0000\sptoken}}
02: \Test{\normalizenumber{-\sptoken\sptoken-\sptoken++\sptoken - 8\sptoken}}
03: \Test{\normalizenumber{+-+00000}}
04: \Test{\normalizenumber{-++++0}}
05: \Test{\normalizenumber{---00000.000010000}}
06: \Test{\normalizenumber{--+-0003.9}}
07: \Test{\normalizenumber{+-+00087}}
08: \Test{\normalizenumber{+ -+00024}}
09: \Test{\normalizenumber{--87.0000}}
10: \Test{\normalizenumber{+--0015.00000010000700000}}
11: \Test{\normalizenumber{+98.0000 }}
12: \Test{\normalizenumber{4.50000}}
13: \Test{\normalizenumber{2.50000 }}
14: \Test{\normalizenumber{7,4}}
15: \Test{\normalizenumber{67}}
16: \Test{\normalizenumber{-15}}
17: \Test{\normalizenumber{-+ +-+ 15 }}
18: \Test{\normalizenumber{67,0000}}
19: \Test{\normalizenumber{67,0000001}}
20: \Test{\normalizenumber{68,0000 }}
21: \Test{\normalizenumber{2,80000}}
22: \Test{\normalizenumber{7,50000 }}
23: \Test{\normalizenumber{1,50000 }}
\kern\dp\strutbox
\hrule
\kern\dp\strutbox
The following don't comply any of these two patterns:
24: \Test{\normalizenumber{}}
25: \Test{\normalizenumber{--++}}
26: \Test{\normalizenumber{--++}}
27: \Test{\normalizenumber{-1.}}
28: \Test{\normalizenumber{3.7.0000 }}
29: \Test{\normalizenumber{8,5,0000 }}
30: \Test{\normalizenumber{8,9.0000 }}
31: \Test{\normalizenumber{9.3,0000 }}
32: \Test{\normalizenumber{A.0000}}
33: \Test{\normalizenumber{1{1}1}}
34: \Test{\normalizenumber{{1},6}}
35: \Test{\normalizenumber{1,}}
36: \Test{\normalizenumber{7,~ / 8()}}
37: \Test{\normalizenumber{1{1}1}}
\kern\dp\strutbox
\hrule
\kern\dp\strutbox
\verb|\def\macroa#1#2{- - + -00012\macrob}%|
\def\macroa#1#2{- - + -00012\macrob}%
\verb|\def\macrob{34.56000}%|
\def\macrob{34.56000}%
\verb|\normalizenumberexpandargfalse|
\normalizenumberexpandargfalse
32: \Test{\normalizenumber{\macroa{7}{8}}}
\verb|\normalizenumberexpandargtrue|
\normalizenumberexpandargtrue
33: \Test{\normalizenumber{\macroa{7}{8}}}
\end{document}