---
title: "The `mvp` package: some timings"
author: "Robin K. S. Hankin"
date: "`r Sys.Date()`"
output:
  pdf_document: default
  html_document:
    df_print: paged
vignette: >
  %\VignetteIndexEntry{mvp_timings}
  %\VignetteEngine{knitr::rmarkdown}
  %\VignetteEncoding{UTF-8}
---

```{r set-options, echo = FALSE}
knitr::opts_chunk$set(collapse = TRUE, comment = "#>", dev = "png", fig.width = 7, fig.height = 3.5, message = FALSE, warning = FALSE)
options(width = 80, tibble.width = Inf)
```

<p style="text-align: right;">
![](`r system.file("help/figures/mvp.png", package = "mvp")`){width=10%}
</p>


Here I present a short analysis of timings for benchmark tasks using
the `mvp` and `spray` packages.  I will show some timings using a
particularly favourable example that exploits the symbolic nature of
the `mvp` package.

```{r}
source("coercion.R")   # low-level functions, e.g. as.mvp()
tp <- function(n,r){kahle(n,r=r,p=seq_len(r),symbols=paste0("x",sprintf("%03d",seq_len(n))))}
k <- tp(9,3)  # test polynomial
mvp_to_spray(k)
k
```

In the above, polynomial `k` has $n=9$ terms of the form $xy^2z^3$.
Coercing `k` to `spray` form would need a $n\times n$ matrix for the
indices, only $3n$ elements of which would be nonzero.  This would be
expected to make [the __spray__
package](https://github.com/RobinHankin/spray) slower, at least for
large $n$, but this does not seem to be the case.

```{r}
library("microbenchmark")
mbm <- function(n,r,p,...){
  k <- tp(n,r)
  spray_k <- mvp_to_spray(k)
  microbenchmark(k^p, spray_k^p,...)
}		  
```

Thus `mbm()` is a unified benchmark execution function:


```{r}
mbm(10,3,2)
mbm(10,3,3)
mbm(10,3,4)
mbm(20,3,2)
mbm(30,3,2)
mbm(40,3,2)
```


In each case above, `spray` is considerably faster.  But if we
consider the simpler case of calculating $(x_1+x_2+\ldots +x_n)^2$ for
different values of $n$ we see `mvp` becoming slightly faster:

```{r}
mbm(10,1,2,times=10)
mbm(20,1,2,times=10)
mbm(50,1,2,times=10)
mbm(100,1,2,times=10)
mbm(200,1,2,times=10)
mbm(300,1,2,times=10)
```