<p><div><div><div><div data-width="100" data-show-faces="false" data-send="true" data-layout="button_count" data-height="21" data-href="https://www.r-bloggers.com/age-bias-plot-changes-in-fsa/"></div></div><div></div></div><div></div></div>
<div>
(This article was first published on <strong><a href="http://derekogle.com/fishR/2017-04-26-AgeBias_inFSA"> fishR Blog</a></strong>, and kindly contributed to <a rel="nofollow" href="https://www.r-bloggers.com/">R-bloggers)</a> </div>
<hr>
<p>In the last two weeks, I have posted twice about modifying <a target="_blank" rel="nofollow" href="http://derekogle.com/fishR/2017-04-14-Modified_AgeBiasPlot">age bias plots</a> and <a target="_blank" rel="nofollow" href="http://derekogle.com/fishR/2017-04-20-Modified_BlandAltmanPlot">Bland-Altman-like plots</a> for comparing age estimates. From those posts, I have decided that I prefer to</p>
<ul>
<li>plot differences between the ages on the y-axis (as compared to the nonreference ages),</li>
<li>plot overlapping points with a transparent color that becomes darker as more points overlap,</li>
<li>when individual points are shown, plot a generalized additive model (GAM) that describes the relationship between the difference in ages and the reference ages or the mean of the two ages (if a reference age is not declared), and</li>
<li>when individual data points are not shown, show the mean and range (rather than confidence intervals) of differences in ages at each reference age with open points representing means where a significant difference between the estimates is evident.</li>
</ul>
<p>I recently updated the <strong>FSA</strong> package so that these preferences are the defaults, while still allowing users some flexibility in creating plots that fit their preferences. Here I explain this new functionality.</p>
<p>The functionality described here is available in the current development version of <strong>FSA</strong> and will eventually (during summer) be on CRAN as version 0.8.13. I welcome any comments or suggestions.</p>
<p>The data used here will again be ages of Lake Whitefish (<em>Coregonus clupeaformis</em>) from Lake Champlain that are available in the <code>WhitefishLC</code> data.frame in <strong>FSA</strong>. These analyses will compare consensus (between two readers) otolith (<code>otolithC</code>) and scale (<code>scaleC</code>) age estimates and otolith ages between two readers (<code>otolith1</code> and <code>otolith2</code>). The consensus otolith age estimates and otolith age estimates from the first reader will be considered as “reference” ages when such a distinction is needed.</p>
<figure>
<pre><code data-lang="r"><span>library</span><span>(</span><span>FSA</span><span>)</span><span>
</span><span>data</span><span>(</span><span>WhitefishLC</span><span>)</span><span>
</span><span>head</span><span>(</span><span>WhitefishLC</span><span>)</span></code></pre>
</figure>
<figure>
<pre><code data-lang="text">##   fishID  tl scale1 scale2 scaleC finray1 finray2 finrayC otolith1
## 1      1 345      3      3      3       3       3       3        3
## 2      2 334      4      3      4       3       3       3        3
## 3      3 348      7      5      6       3       3       3        3
## 4      4 300      4      3      4       3       2       3        3
## 5      5 330      3      3      3       4       3       4        3
## 6      6 316      4      4      4       2       3       3        6
##   otolith2 otolithC
## 1        3        3
## 2        3        3
## 3        3        3
## 4        3        3
## 5        3        3
## 6        5        6</code></pre>
</figure>
<figure>
<pre><code data-lang="r"><span>abSO</span><span> </span><span>&lt;-</span><span> </span><span>ageBias</span><span>(</span><span>scaleC</span><span>~</span><span>otolithC</span><span>,</span><span>data</span><span>=</span><span>WhitefishLC</span><span>,</span><span>
</span><span>nref.lab</span><span>=</span><span>&quot;Scale Age&quot;</span><span>,</span><span>ref.lab</span><span>=</span><span>&quot;Otolith Age&quot;</span><span>)</span><span>
</span><span>abOO</span><span> </span><span>&lt;-</span><span> </span><span>ageBias</span><span>(</span><span>otolith2</span><span>~</span><span>otolith1</span><span>,</span><span>data</span><span>=</span><span>WhitefishLC</span><span>,</span><span>
</span><span>nref.lab</span><span>=</span><span>&quot;Reader 2&quot;</span><span>,</span><span>ref.lab</span><span>=</span><span>&quot;Reader 1&quot;</span><span>)</span></code></pre>
</figure>
<hr>
<h1>Age comparisons with summary statistics</h1>
<p>The default plot of an <code>ageBias()</code> object is a modified age bias plot with the difference in age estimates on the y-axis, the reference age estimates on the x-axis, a reference line at a difference in age estimates of zero, the mean and the range of differences in age estimates shown for each reference age estimate, open points representing age estimates where the mean difference in age estimates is significantly different from zero, solid points representing age estimates where the mean difference in age estimates is not significantly different from zero, a marginal histogram at the top that shows the distribution (and sample sizes) of the reference age estimates, and a marginal histogram on the right that shows the distribution of the difference in age estimates. Confidence intervals for the mean differences in age estimates at each reference age estimate may be added with <code>show.CI=TRUE</code> and individual points can be added with <code>show.pts=TRUE</code>. Other options are described in the <code>ageBias()</code> documentation, which includes a number of examples.</p>
<p>The example in Figure 1 shows that age estimates from scales are less than age estimates from otoliths for otolith age estimates greater than about age-6 or 8, though the statistical evidence is less clear at older ages due to low sample sizes and increased variability. The example in Figure 2 illustrates no systematic difference in age estimates from otoliths between two readers. [<em>Note that the y-axis limits here were widened from the defaults so that the bars in the marginal histogram were not cut off.</em>]</p>
<figure>
<pre><code data-lang="r"><span>plot</span><span>(</span><span>abSO</span><span>)</span></code></pre>
</figure>
<p><img alt="plot of chunk RefSO1" src="https://i2.wp.com/derekogle.com/fishR/figures/RefSO1-1.png?w=456" data-recalc-dims="1"></p>
<p>Figure 1: Mean (points) and range (intervals) of differences in scale and otolith age estimates at each otolith age estimate for Lake Champlain Lake Whitefish. Open points represent mean differences in scale and otolith age estimates that are significantly different from zero (dashed gray horizontal line). Marginal histograms are for otolith age estimates (top) and differences in scale and otolith age estimates (right).</p>
<figure>
<pre><code data-lang="r"><span>plot</span><span>(</span><span>abOO</span><span>,</span><span>ylim</span><span>=</span><span>c</span><span>(</span><span>-2.4</span><span>,</span><span>2.4</span><span>))</span></code></pre>
</figure>
<p><img alt="plot of chunk RefOO1" src="https://i2.wp.com/derekogle.com/fishR/figures/RefOO1-1.png?w=456" data-recalc-dims="1"></p>
<p>Figure 2: Mean (points) and range (intervals) of differences in otolith age estimates between two readers at the estimates for the first reader for Lake Champlain Lake Whitefish. Open points represent mean differences in age estimates that are significantly different from zero (dashed gray horizontal line). Marginal histograms are for age estimates of the first reader (top) and differences in age estimates between readers (right).</p>
<hr>
<h1>Individual points with a GAM smoother</h1>
<p>As discussed in <a target="_blank" rel="nofollow" href="http://derekogle.com/fishR/2017-04-20-Modified_BlandAltmanPlot">this post</a>, differences between two sets of age estimates can be revealed by plotting individual points with a summary for the relationship between the differences in age estimates and the reference or mean age estimates (whichever is used on the x-axis). These examples show how to create a base plot to which a summary can be added. These examples use the mean of the two age estimates on the x-axis, but the plot from the previous section with the reference age estimates on the x-axis could be used (but with <code>show.pts=TRUE</code> to show the individual points and <code>show.range=FALSE</code> to remove the mean and range intervals).</p>
<p>Before making the first example plot, a GAM will be fit to the differences and mean age estimates data. These data are contained in the <code>diff</code> and <code>mean</code> variables in the <code>data</code> object returned in the <code>ageBias()</code> object.</p>
<figure>
<pre><code data-lang="r"><span>head</span><span>(</span><span>abSO</span><span>$</span><span>data</span><span>)</span></code></pre>
</figure>
<figure>
<pre><code data-lang="text">##   scaleC otolithC diff mean
## 1      3        3    0  3.0
## 2      4        3    1  3.5
## 3      6        3    3  4.5
## 4      4        3    1  3.5
## 5      3        3    0  3.0
## 6      4        6   -2  5.0</code></pre>
</figure>
<p>As shown in <a target="_blank" rel="nofollow" href="http://derekogle.com/fishR/2017-04-20-Modified_BlandAltmanPlot">this post</a>, the GAM is fit with <code>gam()</code> using <code>s()</code> from the <code>mgcv</code> package. The mean predicted differences in age estimates, and their standard errors, throughout the range of observed mean age estimates are calculated with <code>predict()</code> using <code>type=&quot;response&quot;</code> and <code>se=TRUE</code>. Approximate 95% confidence intervals for the predicted mean differences in age estimates are computed from normal theory. The code below fits the GAM, creates a vector of mean age estimates at which to make predictions, makes the predictions, and computes the approximate 95% confidence intervals.</p>
<figure>
<pre><code data-lang="r"><span>library</span><span>(</span><span>dplyr</span><span>)</span><span> </span><span># for mutate()
</span><span>library</span><span>(</span><span>mgcv</span><span>)</span><span> </span><span># for gam() and s()
</span><span>mod1</span><span> </span><span>&lt;-</span><span> </span><span>gam</span><span>(</span><span>diff</span><span>~</span><span>s</span><span>(</span><span>mean</span><span>,</span><span>k</span><span>=</span><span>5</span><span>),</span><span>data</span><span>=</span><span>abSO</span><span>$</span><span>data</span><span>)</span><span>
</span><span>tmp</span><span> </span><span>&lt;-</span><span> </span><span>seq</span><span>(</span><span>0</span><span>,</span><span>18</span><span>,</span><span>0.1</span><span>)</span><span>
</span><span>pred1</span><span> </span><span>&lt;-</span><span> </span><span>data.frame</span><span>(</span><span>age</span><span>=</span><span>tmp</span><span>,</span><span>
</span><span>predict</span><span>(</span><span>mod1</span><span>,</span><span>data.frame</span><span>(</span><span>mean</span><span>=</span><span>tmp</span><span>),</span><span>type</span><span>=</span><span>&quot;response&quot;</span><span>,</span><span>se</span><span>=</span><span>TRUE</span><span>))</span><span> </span><span>%>%</span><span>
</span><span>mutate</span><span>(</span><span>LCI</span><span>=</span><span>fit</span><span>-1.96</span><span>*</span><span>se.fit</span><span>,</span><span>UCI</span><span>=</span><span>fit</span><span>+1.96</span><span>*</span><span>se.fit</span><span>)</span><span>
</span><span>head</span><span>(</span><span>pred1</span><span>)</span></code></pre>
</figure>
<figure>
<pre><code data-lang="text">##   age        fit    se.fit       LCI      UCI
## 1 0.0 -0.2479616 0.7058686 -1.631464 1.135541
## 2 0.1 -0.2333355 0.6846088 -1.575169 1.108498
## 3 0.2 -0.2187095 0.6634582 -1.519088 1.081669
## 4 0.3 -0.2040835 0.6424276 -1.463241 1.055075
## 5 0.4 -0.1894574 0.6215291 -1.407654 1.028740
## 6 0.5 -0.1748314 0.6007766 -1.352354 1.002691</code></pre>
</figure>
<p>The base plot of individual differences in age estimates plotted against the mean age estimates is constructed by adding <code>xvals=&quot;mean&quot;</code> to <code>plot()</code>. By default, a histogram for the difference in age estimates is shown on the right. A histogram for the mean age estimates is not shown by default but can be added at the top with <code>xHist=TRUE</code>. The <code>allowAdd=TRUE</code> argument is used so that “items”, like the GAM results, can be added to the main plot (i.e., not the marginal histograms). Note that using <code>allowAdd=TRUE</code> changes the current graphing parameters and that it is good practice to save the current graphing parameters (the first line below) so that they can be reset after finishing the plot (use of <code>par(op)</code> below).</p>
<figure>
<pre><code data-lang="r"><span>op</span><span> </span><span>&lt;-</span><span> </span><span>par</span><span>(</span><span>no.readonly</span><span>=</span><span>TRUE</span><span>)</span><span>
</span><span>plot</span><span>(</span><span>abSO</span><span>,</span><span>xvals</span><span>=</span><span>&quot;mean&quot;</span><span>,</span><span>transparency</span><span>=</span><span>1</span><span>/</span><span>4</span><span>,</span><span>allowAdd</span><span>=</span><span>TRUE</span><span>)</span></code></pre>
</figure>
<p>The GAM results (line at the the predicted means and polygon for the 95% confidence bands) are then added to this plot as described in <a target="_blank" rel="nofollow" href="http://derekogle.com/fishR/2017-04-20-Modified_BlandAltmanPlot">this post</a>.</p>
<figure>
<pre><code data-lang="r"><span>with</span><span>(</span><span>pred1</span><span>,</span><span>polygon</span><span>(</span><span>c</span><span>(</span><span>age</span><span>,</span><span>rev</span><span>(</span><span>age</span><span>)),</span><span>c</span><span>(</span><span>LCI</span><span>,</span><span>rev</span><span>(</span><span>UCI</span><span>)),</span><span>
</span><span>border</span><span>=</span><span>NA</span><span>,</span><span>col</span><span>=</span><span>col2rgbt</span><span>(</span><span>&quot;gray80&quot;</span><span>,</span><span>1</span><span>/</span><span>2</span><span>)))</span><span>
</span><span>lines</span><span>(</span><span>fit</span><span>~</span><span>age</span><span>,</span><span>data</span><span>=</span><span>pred1</span><span>,</span><span>lwd</span><span>=</span><span>2</span><span>,</span><span>lty</span><span>=</span><span>2</span><span>)</span></code></pre>
</figure>
<p>Finally, the graphing parameters are returned to their original values.</p>
<figure>
<pre><code data-lang="r"><span>par</span><span>(</span><span>op</span><span>)</span></code></pre>
</figure>
<p>The example in Figure 3 suggests that the two age estimates generally agree to a mean age of about 5, after which ages estimated from scales are less than ages estimated from otoliths. The example in Figure 4 suggests no difference in age estimates between the two readers for all mean ages.</p>
<p><img alt="plot of chunk MeanSO1" src="https://i0.wp.com/derekogle.com/fishR/figures/MeanSO1-1.png?w=456" data-recalc-dims="1"></p>
<p>Figure 3: Differences in scale and otolith age estimates at each mean age estimate for Lake Champlain Lake Whitefish. The dashed gray horizontal line is at 0, which represents no difference between scale and otolith age estimates. The dashed black line and gray polygon represent the mean and 95% confidence band for the predicted mean difference in age estimates from a generalized additive model. The right marginal histogram is for the differences in scale and otolith age estimates.</p>
<p><img alt="plot of chunk MeanOO1" src="https://i0.wp.com/derekogle.com/fishR/figures/MeanOO1-1.png?w=456" data-recalc-dims="1"></p>
<p>Figure 4: Differences in otolith age estimates between two readers at each mean age estimate for Lake Champlain Lake Whitefish. The dashed gray horizontal line is at 0, which represents no difference in age estimates between the two readers. The dashed black line and gray polygon represent the mean and 95% confidence band for the predicted mean difference in age estimates from a generalized additive model. The right marginal histogram is for the differences in age estimates between the two readers.</p>
<hr>
<h1>Some “traditional” plots</h1>
<p>My modification of the traditional age bias plot of Campana et al. (1995) is constructed from the <code>ageBias()</code> object with <code>plotAB()</code> (Figure 5). Some simple modifications of this plot are demonstrated in the documentation and examples for <code>plotAB()</code>.</p>
<figure>
<pre><code data-lang="r"><span>plotAB</span><span>(</span><span>abSO</span><span>)</span></code></pre>
</figure>
<p><img alt="plot of chunk AgeBiasSO1" src="https://i2.wp.com/derekogle.com/fishR/figures/AgeBiasSO1-1.png?w=456" data-recalc-dims="1"></p>
<p>Figure 5: Mean (points) and 95% confidence intervals of scale age estimates at each otolith age estimate for Lake Champlain Lake Whitefish. The dashed gray line represents age estimates that agree. Open points (with red confidence intervals) represent mean scale age estimates that differ significantly from the corresponding otolith age estimate.</p>
<p>Finally, some users prefer a simple plot that shows the number of individuals at each point (Figure 6). This plot is constructed with <code>plotAB()</code> using <code>what=&quot;nunbers&quot;</code>.</p>
<figure>
<pre><code data-lang="r"><span>plotAB</span><span>(</span><span>abSO</span><span>,</span><span>what</span><span>=</span><span>&quot;numbers&quot;</span><span>)</span></code></pre>
</figure>
<p><img alt="plot of chunk AgeBiasNumSO1" src="https://i1.wp.com/derekogle.com/fishR/figures/AgeBiasNumSO1-1.png?w=456" data-recalc-dims="1"></p>
<p>Figure 6: Number of individuals by each scale and otolith age estimate combination for Lake Champlain Lake Whitefish. The dashed gray line represents age estimates that agree.</p>
<hr>
<h3>References</h3>
<ul>
<li>
<p>Campana, S.E., M.C. Annand, and J.I. McMillan. 1995. Graphical and statistical methods for determining the consistency of age determinations. Transactions of the American Fisheries Society 124:131-138.</p>
</li>
<li>
<p>Ogle, D.H. 2015. <a target="_blank" rel="nofollow" href="http://derekogle.com/IFAR/">Introductory Fisheries Analyses with R book</a>. CRC Press.</p>
</li>
</ul>
<hr>
<p>
<div>
<div>To <strong>leave a comment</strong> for the author, please follow the link and comment on their blog: <strong><a href="http://derekogle.com/fishR/2017-04-26-AgeBias_inFSA"> fishR Blog</a></strong>.</div>
<hr>
<a rel="nofollow" href="https://www.r-bloggers.com/">R-bloggers.com</a> offers <strong><a rel="nofollow" href="https://feedburner.google.com/fb/a/mailverify?uri=RBloggers">daily e-mail updates</a></strong> about <a title="The R Project for Statistical Computing" rel="nofollow" href="https://www.r-project.org/">R</a> news and <a title="R tutorials" rel="nofollow" href="https://www.r-bloggers.com/search/tutorial">tutorials</a> on topics such as: <a title="Data science" rel="nofollow" href="https://www.r-bloggers.com/search/data%20science">Data science</a>, <a title="Big Data" rel="nofollow" href="https://www.r-bloggers.com/search/Big%20Data">Big Data, <a title="R jobs" rel="nofollow" href="https://www.r-users.com/">R jobs</a>, visualization (<a title="ggplot and ggplot2 tutorials" rel="nofollow" href="https://www.r-bloggers.com/search/ggplot2">ggplot2</a>, <a title="Boxplots using lattice and ggplot2 tutorials" rel="nofollow" href="https://www.r-bloggers.com/search/boxplot">Boxplots</a>, <a title="Maps and gis" rel="nofollow" href="https://www.r-bloggers.com/search/map">maps</a>, <a title="Animation in R" rel="nofollow" href="https://www.r-bloggers.com/search/animation">animation</a>), programming (<a title="RStudio IDE for R" rel="nofollow" href="https://www.r-bloggers.com/search/RStudio">RStudio</a>, <a title="Sweave and literate programming" rel="nofollow" href="https://www.r-bloggers.com/search/sweave">Sweave</a>, <a title="LaTeX in R" rel="nofollow" href="https://www.r-bloggers.com/search/LaTeX">LaTeX</a>, <a title="SQL and databases" rel="nofollow" href="https://www.r-bloggers.com/search/SQL">SQL</a>, <a title="Eclipse IDE for R" rel="nofollow" href="https://www.r-bloggers.com/search/eclipse">Eclipse</a>, <a title="git and github, Version Control System" rel="nofollow" href="https://www.r-bloggers.com/search/git">git</a>, <a title="Large data in R using Hadoop" rel="nofollow" href="https://www.r-bloggers.com/search/hadoop">hadoop</a>, <a title="Web Scraping of google, facebook, yahoo, twitter and more using R" rel="nofollow" href="https://www.r-bloggers.com/search/Web+Scraping">Web Scraping</a>) statistics (<a title="Regressions and ANOVA analysis tutorials" rel="nofollow" href="https://www.r-bloggers.com/search/regression">regression</a>, <a title="principal component analysis tutorial" rel="nofollow" href="https://www.r-bloggers.com/search/PCA">PCA</a>, <a title="Time series" rel="nofollow" href="https://www.r-bloggers.com/search/time+series">time series</a>, <a title="finance trading" rel="nofollow" href="https://www.r-bloggers.com/search/trading">trading</a>) and more...
<img height="1" alt="" width="1" src="http://feeds.feedburner.com/~r/RBloggers/~4/tiinNKKbRSg"></a></div>