如果我有一个十进制数,比如说0.09155
,但我想显示小数点后两位数字的四舍五入版本:0.09
。
标准方法是使用\pgfmathprintnumber[fixed, precision=2]{0.09155}
。
0.09
所以我的问题是:我能在这里通过以下方式获得想要的值吗数学-计算,这意味着不使用pgfmathprintnumber
?
\documentclass[margin=5pt, varwidth]{standalone}
\usepackage{tikz}
\begin{document}
\pgfmathsetmacro\x{0.09155}
$x = \x$, but
$x \approx \pgfmathprintnumber[fixed, precision=2]{\x}$
\end{document}
答案1
下面定义了一个roundn
函数,pgfmath
它接受两个参数,一个是需要四舍五入的数字,第二个是希望数字四舍五入到的位数。
\documentclass[]{article}
\usepackage{pgfmath}
\pgfmathsetmacro\x{0.09155}
\pgfmathdeclarefunction{roundn}{2}
{\pgfmathparse{round(#1 * 10^(#2)) / (10^(#2))}}
\begin{document}
$x = \x$, but
$x \approx \pgfmathparse{roundn(\x,2)}\pgfmathresult$
\end{document}
答案2
为什么不与xfp 封装?
\documentclass[margin=5pt, varwidth]{standalone}
\usepackage{tikz}
\usepackage{xfp}
\begin{document}
\pgfmathsetmacro\x{0.09155}
$x = \x$, but
$x \approx \pgfmathprintnumber[fixed, precision=2]{\x}$
\bigskip
With xfp package:
$x = \x$, but
$x \approx \fpeval{round(\x,2)}$
\end{document}
答案3
这是一个自制版本tokcycle
(即没有 pgf)。它四舍五入到 中指定的级别\savedigits
。
\documentclass{article}
\usepackage{tokcycle}
\newcounter{decs}
\def\savedigits{2}
\newif\iferr
\newif\iffounddot
\newcommand\roundit[1]{%
\errfalse
\setcounter{decs}{0}%
\founddotfalse% MADE T WHEN DECIMAL HAS BEEN 1ST LOCATED
\tokcycle% CYCLE THROOUGH EACH TOKEN
{\tctestifx{.##1}%
{\addcytoks{##1}%
\iffounddot\errtrue\fi\founddottrue\setcounter{decs}{0}}% IF .
{\tctestifnum{`##1>`/}%
{\tctestifnum{`##1<`:}%
{%
\iffounddot\stepcounter{decs}\fi%
\ifnum\thedecs<\savedigits\relax\addcytoks{##1}\else
\ifnum\thedecs=\savedigits\relax\addcytoks{\roundlast ##1}\else
\ifnum\thedecs=\numexpr\savedigits+1 \addcytoks{##1}\fi\fi\fi
}%
{\errtrue}% IF ASCII > `9
}%
{\errtrue}% IF ASCII < `0
}%
}% APPLY ABOVE LOGIC FOR CHAR TOKENS
{\errtrue}% IF BRACES
{\errtrue}% IF CONTROL SEQUENCE
{}% IGNORE SPACES
{#1}% THE ARGUMENT
\addcytoks{\space}
\iferr ERROR\else\the\cytoks\fi
}
\newcommand\roundlast[2]{\ifnum0#2>4 \the\numexpr#1+1 \else#1\fi}
\begin{document}
\noindent
0) \roundit{0.09155}\\
1) \roundit{12.3}\\
2) \roundit{0.127}\\
3) \roundit{1.2.3}\\
4) \roundit{1.3\today}\\
5) \roundit{321.345 678}\\
6) \roundit{000321.305}\\
7) \roundit{.006 300 345}\\
8) \roundit{0003x1.345}\\
9) \roundit{1230}\\
9a) \roundit{1230.}\\
A) \roundit{123.078}\\
B) \roundit{0003;345}\\
\end{document}
如果您不介意省去错误检查,这里有一个不同的令牌循环,它采用了一个新的(2021-05-27)功能来提前查看输入流,根据需要推送和弹出令牌,以及根据循环内发生的情况截断循环。
\documentclass{article}
\usepackage{tokcycle}[2021-05-27]
\newcommand\roundit[1]{\tokcycle
{\ifx.##1.%
\tcpop\tenths
\tcpop\hundredths
\tcpop\thousandths
\ifnum 0\thousandths>4
\tenths\the\numexpr\hundredths+1 \else\tenths\hundredths\fi
\tcpush{\noexpand\truncatecycle}%
\else
##1%
\fi
}% DO THE ABOVE FOR EACH CHARACTER
{\processtoks{\truncatecycle}}% IF GROUP
{\truncatecycle}% IF MACRO
{##1}% IF SPACE
{#1}}
\begin{document}
\noindent
0) \roundit{0.09155}\\
1) \roundit{12.3}\\
2) \roundit{0.127}\\
5) \roundit{321.345 678}\\
6) \roundit{000321.305}\\
7) \roundit{.006 300 345}\\
9) \roundit{1230}\\
9a) \roundit{1230.}\\
A) \roundit{123.078}\\
\end{document}
答案4
由于 pgfmath 计算不精确,最好使用 pgfmathprintnumber:
\documentclass[margin=5mm, varwidth]{standalone}
\usepackage{tikz}
\pgfmathdeclarefunction{roundn}{2}{%
\pgfmathparse{#1}%
\pgfmathparse{"\pgfmathprintnumber[fixed, precision=#2]{\pgfmathresult}"}%
}
\begin{document}
Test: \pgfmathparse{roundn(1.23456,2)}\pgfmathresult
Test: \pgfmathparse{roundn(sqrt(2),3)}\pgfmathresult
\end{document}