![編輯](https://rvso.com/image/328472/%E7%B7%A8%E8%BC%AF.png)
我遇到的問題是,在下圖中,A 的座標文字附近的右側節點缺失。問題的根源在於數據中的捨入誤差:它們的總和應該是 100,但在 A 中卻多了一點。避免這種情況的最佳方法是什麼?簡單地將 A 向下舍入並不是一種選擇。我有大量這樣的圖,有更多的列,幾乎每個圖中都有一行的總和有點太大。
\documentclass[]{article}
\usepackage[T1]{fontenc}
\usepackage[utf8]{inputenc}
\usepackage{pgfplots}
\pgfplotsset{compat=1.13}
\usepackage{pgfplotstable}
\pgfplotsset{
my stackbar plot/.style={
xbar stacked,
xmin=0,xmax=100,
symbolic y coords={A,B},
ytick=data,
nodes near coords={xxx},}}
\begin{document}
\begin{tikzpicture}
\pgfplotstableread[col sep=space]{
text -- -
B 50 50
A 50.01 50
}\data
\begin{axis}[my stackbar plot,]
\addplot table [x expr = \thisrow{--},y=text] {\data};
\addplot table [x expr = \thisrow{-}, y=text] {\data};
\end{axis}
\end{tikzpicture}
\end{document}
答案1
我認為最明智的解決方案是標準化這些價值。這是我最後使用的程式碼的簡化版本:
\documentclass[]{article}
\usepackage[T1]{fontenc}
\usepackage[utf8]{inputenc}
\usepackage{pgfplots}
\pgfplotsset{compat=1.13}
\usepackage{pgfplotstable}
\pgfplotsset{
my stackbar plot/.style={
xbar stacked,
xmin=0,xmax=100,
symbolic y coords={A,B},
ytick=data,
nodes near coords={xxx},}}
\begin{document}
\begin{tikzpicture}
\pgfplotstableread[col sep=space]{
text -- -
B 50 50
A 50.01 50
}\data
\pgfplotstablecreatecol[create col/expr={\thisrow{--}+\thisrow{-}}]{sum}\data
\pgfplotstablecreatecol[create col/expr={\thisrow{--}/\thisrow{sum}*100}]{--}\data
\pgfplotstablecreatecol[create col/expr={\thisrow{-}/\thisrow{sum}*100}]{-}\data
\begin{axis}[my stackbar plot,]
\addplot table [x expr = \thisrow{--},y=text] {\data};
\addplot table [x expr = \thisrow{-}, y=text] {\data};
\end{axis}
\end{tikzpicture}
\end{document}
編輯
進一步的測試表明,正常化是不夠的。總數仍可能略大於 100,因此標記可能會遺失。有必要截斷這些值,請參閱pgfplots:正確的捨入問題。
答案2
也可以僅對加起來不等於 100 的行中的值進行標準化:
\documentclass[]{article}
\usepackage[T1]{fontenc}
\usepackage[utf8]{inputenc}
\usepackage{pgfplots}
\pgfplotsset{compat=1.13}
\usepackage{pgfplotstable}
\pgfplotsset{
my stackbar plot/.style={
xbar stacked,
xmin=0,xmax=100,
symbolic y coords={A,B},
ytick=data,
nodes near coords={xxx},}}
\begin{document}
\begin{tikzpicture}
\pgfplotstableread[col sep=space]{
text -- -
B 50 50
A 50.01 50
}\data
\pgfplotstablecreatecol[create col/expr={\thisrow{--}+\thisrow{-}}]{sum}\data
% normalize only if the sum is not 100
\pgfplotsinvokeforeach{--,-}{%
\pgfplotstablemodifyeachcolumnelement{#1}\of\data\as\wert{%
\pgfplotstablegetelem{\pgfplotstablerow}{sum}\of\data%
\pgfmathparse{\pgfplotsretval==100?\wert:\wert*100/\pgfplotsretval}%
\edef\wert{\pgfmathresult}
}%
}
\begin{axis}[my stackbar plot,]
\addplot table [x expr = \thisrow{--},y=text] {\data};
\addplot table [x expr = \thisrow{-}, y=text] {\data};
\end{axis}
\end{tikzpicture}
\end{document}
以同樣的方式,可以僅更改加起來超過 100 的行中的值,使用
% normalize only if the sum is >100
\pgfplotsinvokeforeach{--,-}{%
\pgfplotstablemodifyeachcolumnelement{#1}\of\data\as\wert{%
\pgfplotstablegetelem{\pgfplotstablerow}{sum}\of\data%
\pgfmathparse{\pgfplotsretval<=100?\wert:\wert*100/\pgfplotsretval}%
\edef\wert{\pgfmathresult}
}%
}