├── .Rbuildignore ├── .github ├── .gitignore └── workflows │ ├── R-CMD-check.yaml │ └── test-coverage.yaml ├── .gitignore ├── CRAN-SUBMISSION ├── DESCRIPTION ├── LICENSE ├── LICENSE.md ├── NAMESPACE ├── NEWS.md ├── R ├── advans.R ├── algebraics.R ├── assemblerr-package.R ├── ast.R ├── compartment.R ├── conversion-compartment-nm.R ├── conversion-input_variable-nm.R ├── conversion-meta-nm.R ├── conversion-nm.R ├── conversion-observation-nm.R ├── conversion-parameter-nm.R ├── conversion-tasks-nm.R ├── conversion.R ├── declaration-creation.R ├── declaration.R ├── description.R ├── facet.R ├── generics.R ├── input_variable.R ├── issues.R ├── meta.R ├── model-options.R ├── model.R ├── nm_model.R ├── node-classes.R ├── observation.R ├── parameter-values.R ├── parameter.R ├── pk_component.R ├── pk_model.R ├── rendering.R ├── statement.R ├── tasks.R ├── test-helpers.R ├── util.R └── variables.R ├── README.Rmd ├── README.md ├── _pkgdown.yml ├── assemblerr.Rproj ├── codecov.yml ├── cran-comments.md ├── docs ├── 404.html ├── LICENSE-text.html ├── LICENSE.html ├── articles │ ├── getting-started.html │ ├── index.html │ └── introduction.html ├── authors.html ├── bootstrap-toc.css ├── bootstrap-toc.js ├── dev │ ├── 404.html │ ├── LICENSE-text.html │ ├── LICENSE.html │ ├── articles │ │ ├── getting-started.html │ │ └── index.html │ ├── authors.html │ ├── bootstrap-toc.css │ ├── bootstrap-toc.js │ ├── docsearch.css │ ├── docsearch.js │ ├── index.html │ ├── link.svg │ ├── news │ │ └── index.html │ ├── pkgdown.css │ ├── pkgdown.js │ ├── pkgdown.yml │ ├── reference │ │ ├── Rplot001.png │ │ ├── algebraic.html │ │ ├── assemblerr-package.html │ │ ├── assemblerr-vctrs.html │ │ ├── assemblerr_options.html │ │ ├── c-IssueList-method.html │ │ ├── check.html │ │ ├── compartment.html │ │ ├── dcl_add.html │ │ ├── dcl_id-set.html │ │ ├── dcl_id.html │ │ ├── declaration.html │ │ ├── facet_names_to_labels.html │ │ ├── figures │ │ │ └── README-pressure-1.png │ │ ├── flow.html │ │ ├── index.html │ │ ├── input_variables.html │ │ ├── interp.html │ │ ├── is_valid_lhs.html │ │ ├── md_doc_links_for_package_functions.html │ │ ├── model-variable-selection.html │ │ ├── model.html │ │ ├── names-NamedFacet-method.html │ │ ├── new_declaration.html │ │ ├── nm_model.html │ │ ├── nm_pk.html │ │ ├── nm_theta.html │ │ ├── obs_additive.html │ │ ├── obs_combined.html │ │ ├── obs_proportional.html │ │ ├── pipe.html │ │ ├── pk_absorption_fo.html │ │ ├── pk_absorption_fo_lag.html │ │ ├── pk_absorption_fo_transit.html │ │ ├── pk_absorption_fo_zo.html │ │ ├── pk_absorption_zo.html │ │ ├── pk_absorption_zo_lag.html │ │ ├── pk_distribution_1cmp.html │ │ ├── pk_distribution_2cmp.html │ │ ├── pk_distribution_3cmp.html │ │ ├── pk_elimination_linear.html │ │ ├── pk_elimination_linear_nl.html │ │ ├── pk_elimination_nl.html │ │ ├── pk_model.html │ │ ├── plus-BuildingBlock-BuildingBlock-method.html │ │ ├── plus-BuildingBlock-NULL-method.html │ │ ├── print_shortened_tree_description.html │ │ ├── prm_log_normal.html │ │ ├── prm_logit_normal.html │ │ ├── prm_no_var.html │ │ ├── prm_normal.html │ │ ├── render.html │ │ ├── transform_ast.html │ │ ├── tsk_estimation.html │ │ ├── tsk_output.html │ │ └── xtfrm-IssueList-method.html │ └── sitemap.xml ├── docsearch.css ├── docsearch.js ├── index.html ├── link.svg ├── news │ └── index.html ├── pkgdown.css ├── pkgdown.js ├── pkgdown.yml ├── reference │ ├── Rplot001.png │ ├── algebraic.html │ ├── assemblerr-package.html │ ├── assemblerr-vctrs.html │ ├── assemblerr_options.html │ ├── c-IssueList-method.html │ ├── check.html │ ├── compartment.html │ ├── dcl_add.html │ ├── dcl_id-set.html │ ├── dcl_id.html │ ├── declaration.html │ ├── facet_names_to_labels.html │ ├── figures │ │ └── README-pressure-1.png │ ├── flow.html │ ├── index.html │ ├── input_variables.html │ ├── interp.html │ ├── is_valid_lhs.html │ ├── md_doc_links_for_package_functions.html │ ├── model-variable-selection.html │ ├── model.html │ ├── names-NamedFacet-method.html │ ├── new_declaration.html │ ├── nm_model.html │ ├── nm_pk.html │ ├── nm_theta.html │ ├── obs_additive.html │ ├── obs_combined.html │ ├── obs_proportional.html │ ├── pipe.html │ ├── pk_absorption_fo.html │ ├── pk_absorption_fo_lag.html │ ├── pk_absorption_fo_transit.html │ ├── pk_absorption_fo_zo.html │ ├── pk_absorption_zo.html │ ├── pk_absorption_zo_lag.html │ ├── pk_distribution_1cmp.html │ ├── pk_distribution_2cmp.html │ ├── pk_distribution_3cmp.html │ ├── pk_elimination_linear.html │ ├── pk_elimination_linear_nl.html │ ├── pk_elimination_nl.html │ ├── pk_model.html │ ├── plus-BuildingBlock-BuildingBlock-method.html │ ├── plus-BuildingBlock-NULL-method.html │ ├── print_shortened_tree_description.html │ ├── prm_log_normal.html │ ├── prm_logit_normal.html │ ├── prm_no_var.html │ ├── prm_normal.html │ ├── render.html │ ├── transform_ast.html │ ├── tsk_estimation.html │ ├── tsk_output.html │ └── xtfrm-IssueList-method.html └── sitemap.xml ├── man ├── algebraic.Rd ├── assemblerr-package.Rd ├── assemblerr-vctrs.Rd ├── assemblerr_options.Rd ├── c-IssueList-method.Rd ├── check.Rd ├── compartment.Rd ├── dcl_add.Rd ├── dcl_id-set.Rd ├── dcl_id.Rd ├── declaration.Rd ├── facet_names_to_labels.Rd ├── figures │ └── README-pressure-1.png ├── flow.Rd ├── input_variables.Rd ├── interp.Rd ├── is_valid_lhs.Rd ├── md_doc_links_for_package_functions.Rd ├── model-variable-selection.Rd ├── model.Rd ├── names-NamedFacet-method.Rd ├── new_declaration.Rd ├── nm_model.Rd ├── nm_pk.Rd ├── nm_theta.Rd ├── obs_additive.Rd ├── obs_combined.Rd ├── obs_proportional.Rd ├── pipe.Rd ├── pk_absorption_fo.Rd ├── pk_absorption_fo_lag.Rd ├── pk_absorption_fo_transit.Rd ├── pk_absorption_fo_zo.Rd ├── pk_absorption_zo.Rd ├── pk_absorption_zo_lag.Rd ├── pk_distribution_1cmp.Rd ├── pk_distribution_2cmp.Rd ├── pk_distribution_3cmp.Rd ├── pk_elimination_linear.Rd ├── pk_elimination_linear_nl.Rd ├── pk_elimination_nl.Rd ├── pk_model.Rd ├── plus-BuildingBlock-BuildingBlock-method.Rd ├── plus-BuildingBlock-NULL-method.Rd ├── print_shortened_tree_description.Rd ├── prm_log_normal.Rd ├── prm_logit_normal.Rd ├── prm_no_var.Rd ├── prm_normal.Rd ├── render.Rd ├── rmd │ ├── observation-model.Rmd │ ├── parameter-model.Rmd │ ├── pk-component.Rmd │ └── tasks.Rmd ├── transform_ast.Rd ├── tsk_estimation.Rd ├── tsk_output.Rd └── xtfrm-IssueList-method.Rd ├── renv.lock ├── renv ├── .gitignore └── activate.R ├── tests ├── testthat.R └── testthat │ ├── _snaps │ ├── console-printing.md │ ├── issues.md │ ├── model.md │ └── pk-model.md │ ├── integration-tests │ └── test-nonmem-integration.R │ ├── setup.R │ ├── test-console-printing.R │ ├── test-declaration.R │ ├── test-facet.R │ ├── test-global-error-checking.R │ ├── test-issues.R │ ├── test-local-error-checking.R │ ├── test-model.R │ ├── test-nodes.R │ ├── test-ode-model.R │ ├── test-pk-model.R │ ├── test-statement.R │ ├── test-tasks.R │ ├── test-test-helpers.R │ ├── test-util.R │ └── test-variable-renaming.R └── vignettes ├── concepts.bak ├── experimental.bak └── getting-started.Rmd /.Rbuildignore: -------------------------------------------------------------------------------- 1 | ^.*\.Rproj$ 2 | ^\.Rproj\.user$ 3 | ^renv$ 4 | ^renv\.lock$ 5 | ^LICENSE\.md$ 6 | ^README\.Rmd$ 7 | ^\.travis\.yml$ 8 | ^codecov\.yml$ 9 | ^scratch$ 10 | ^_pkgdown\.yml$ 11 | ^docs$ 12 | ^pkgdown$ 13 | ^\.github$ 14 | ^cran-comments\.md$ 15 | ^CRAN-RELEASE$ 16 | ^CRAN-SUBMISSION$ 17 | -------------------------------------------------------------------------------- /.github/.gitignore: -------------------------------------------------------------------------------- 1 | *.html 2 | -------------------------------------------------------------------------------- /.github/workflows/R-CMD-check.yaml: -------------------------------------------------------------------------------- 1 | # For help debugging build failures open an issue on the RStudio community with the 'github-actions' tag. 2 | # https://community.rstudio.com/new-topic?category=Package%20development&tags=github-actions 3 | on: 4 | push: 5 | branches: 6 | - main 7 | - master 8 | pull_request: 9 | branches: 10 | - main 11 | - master 12 | 13 | name: R-CMD-check 14 | 15 | jobs: 16 | R-CMD-check: 17 | runs-on: ${{ matrix.config.os }} 18 | 19 | name: ${{ matrix.config.os }} (${{ matrix.config.r }}) 20 | 21 | strategy: 22 | fail-fast: false 23 | matrix: 24 | config: 25 | - {os: windows-latest, r: 'release'} 26 | - {os: macOS-latest, r: 'release'} 27 | - {os: ubuntu-20.04, r: 'release', rspm: "https://packagemanager.rstudio.com/cran/__linux__/focal/latest"} 28 | - {os: ubuntu-20.04, r: 'devel', rspm: "https://packagemanager.rstudio.com/cran/__linux__/focal/latest", http-user-agent: "R/4.1.0 (ubuntu-20.04) R (4.1.0 x86_64-pc-linux-gnu x86_64 linux-gnu) on GitHub Actions" } 29 | 30 | env: 31 | R_REMOTES_NO_ERRORS_FROM_WARNINGS: true 32 | RSPM: ${{ matrix.config.rspm }} 33 | GITHUB_PAT: ${{ secrets.GITHUB_TOKEN }} 34 | 35 | steps: 36 | - uses: actions/checkout@v2 37 | 38 | - uses: r-lib/actions/setup-r@v1 39 | with: 40 | r-version: ${{ matrix.config.r }} 41 | 42 | - uses: r-lib/actions/setup-pandoc@v1 43 | 44 | - name: Query dependencies 45 | run: | 46 | install.packages('remotes') 47 | saveRDS(remotes::dev_package_deps(dependencies = TRUE), ".github/depends.Rds", version = 2) 48 | writeLines(sprintf("R-%i.%i", getRversion()$major, getRversion()$minor), ".github/R-version") 49 | shell: Rscript {0} 50 | 51 | - name: Restore R package cache 52 | uses: actions/cache@v2 53 | with: 54 | path: ${{ env.R_LIBS_USER }} 55 | key: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1-${{ hashFiles('.github/depends.Rds') }} 56 | restore-keys: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1- 57 | 58 | - name: Install system dependencies 59 | if: runner.os == 'Linux' 60 | run: | 61 | while read -r cmd 62 | do 63 | eval sudo $cmd 64 | done < <(Rscript -e 'writeLines(remotes::system_requirements("ubuntu", "20.04"))') 65 | 66 | - name: Install dependencies 67 | run: | 68 | remotes::install_deps(dependencies = TRUE) 69 | remotes::install_cran("rcmdcheck") 70 | shell: Rscript {0} 71 | 72 | - name: Check 73 | env: 74 | _R_CHECK_CRAN_INCOMING_REMOTE_: false 75 | run: | 76 | options(crayon.enabled = TRUE) 77 | rcmdcheck::rcmdcheck(args = c("--no-manual", "--as-cran"), error_on = "warning", check_dir = "check") 78 | shell: Rscript {0} 79 | 80 | - name: Upload check results 81 | if: failure() 82 | uses: actions/upload-artifact@main 83 | with: 84 | name: ${{ runner.os }}-r${{ matrix.config.r }}-results 85 | path: check 86 | -------------------------------------------------------------------------------- /.github/workflows/test-coverage.yaml: -------------------------------------------------------------------------------- 1 | on: 2 | push: 3 | branches: 4 | - main 5 | - master 6 | pull_request: 7 | branches: 8 | - main 9 | - master 10 | 11 | name: test-coverage 12 | 13 | jobs: 14 | test-coverage: 15 | runs-on: macOS-latest 16 | env: 17 | GITHUB_PAT: ${{ secrets.GITHUB_TOKEN }} 18 | steps: 19 | - uses: actions/checkout@v2 20 | 21 | - uses: r-lib/actions/setup-r@v1 22 | 23 | - uses: r-lib/actions/setup-pandoc@v1 24 | 25 | - name: Query dependencies 26 | run: | 27 | install.packages('remotes') 28 | saveRDS(remotes::dev_package_deps(dependencies = TRUE), ".github/depends.Rds", version = 2) 29 | writeLines(sprintf("R-%i.%i", getRversion()$major, getRversion()$minor), ".github/R-version") 30 | shell: Rscript {0} 31 | 32 | - name: Restore R package cache 33 | uses: actions/cache@v2 34 | with: 35 | path: ${{ env.R_LIBS_USER }} 36 | key: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1-${{ hashFiles('.github/depends.Rds') }} 37 | restore-keys: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1- 38 | 39 | - name: Install dependencies 40 | run: | 41 | install.packages(c("remotes")) 42 | remotes::install_deps(dependencies = TRUE) 43 | remotes::install_cran("covr") 44 | shell: Rscript {0} 45 | 46 | - name: Test coverage 47 | run: covr::codecov() 48 | shell: Rscript {0} 49 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | 2 | # Rstudio files 3 | .Rproj.user 4 | .Rproj 5 | .Rhistory 6 | .RData 7 | .DS_Store 8 | .Rprofile 9 | # Built vignettes 10 | vignettes/*.html 11 | vignettes/*.R 12 | inst/doc 13 | scratch 14 | 15 | -------------------------------------------------------------------------------- /CRAN-SUBMISSION: -------------------------------------------------------------------------------- 1 | Version: 0.1.1 2 | Date: 2022-01-11 20:14:27 UTC 3 | SHA: 2349ac9490ed5a92993bc5113e3b0de138fb3611 4 | -------------------------------------------------------------------------------- /DESCRIPTION: -------------------------------------------------------------------------------- 1 | Package: assemblerr 2 | Title: Assembly of Pharmacometric Models 3 | Description: Construct pharmacometric nonlinear mixed effect models by combining 4 | predefined model components and automatically generate model code for NONMEM. 5 | Models are created by combining parameter and observation models, algebraic 6 | relationships, compartments, and flows. Pharmacokinetic models can be assembled 7 | from the higher-order components: absorption, distribution, and elimination. 8 | The generated code is optimized for performance by recognizing, for example, 9 | linear differential equations or differential equations with an analytic 10 | solution. 11 | Version: 0.1.2 12 | Authors@R: 13 | c( 14 | person(given = "Sebastian", 15 | family = "Ueckert", 16 | role = c("aut", "cre","cph"), 17 | email = "sebastian.ueckert@gmail.com", 18 | comment = c(ORCID = "0000-0002-3712-0255")), 19 | person(given = "Mats O.", 20 | family = "Karlsson", 21 | role = c("sad")), 22 | person(given = "Andrew C.", 23 | family = "Hooker", 24 | role = c("sad")), 25 | person(given = "Rikard", 26 | family = "Nordgren", 27 | role = c("sad")), 28 | person(given = "Simon", 29 | family = "Carter", 30 | role = c("rev")), 31 | person(given = "Simon", 32 | family = "Buatois", 33 | role = c("rev")), 34 | person(given = "João A.", 35 | family = "Abrantes", 36 | role = c("rev")), 37 | person("F. Hoffmann-La Roche Ltd.", 38 | role = c("fnd")) 39 | ) 40 | License: MIT + file LICENSE 41 | Encoding: UTF-8 42 | Suggests: 43 | testthat (>= 3.0.2), 44 | knitr, 45 | rmarkdown, 46 | covr, 47 | withr, 48 | markdown, 49 | devtools 50 | Imports: 51 | purrr (>= 0.3.0), 52 | rlang, 53 | magrittr, 54 | methods, 55 | glue, 56 | vctrs (>= 0.3.4), 57 | cli (>= 2.1.0), 58 | tidyselect 59 | VignetteBuilder: knitr 60 | RoxygenNote: 7.2.1 61 | ByteCompile: true 62 | Collate: 63 | 'advans.R' 64 | 'generics.R' 65 | 'facet.R' 66 | 'conversion.R' 67 | 'model.R' 68 | 'pk_model.R' 69 | 'rendering.R' 70 | 'statement.R' 71 | 'nm_model.R' 72 | 'declaration-creation.R' 73 | 'declaration.R' 74 | 'algebraics.R' 75 | 'assemblerr-package.R' 76 | 'ast.R' 77 | 'compartment.R' 78 | 'conversion-compartment-nm.R' 79 | 'input_variable.R' 80 | 'conversion-input_variable-nm.R' 81 | 'meta.R' 82 | 'conversion-meta-nm.R' 83 | 'conversion-nm.R' 84 | 'observation.R' 85 | 'conversion-observation-nm.R' 86 | 'parameter.R' 87 | 'conversion-parameter-nm.R' 88 | 'node-classes.R' 89 | 'tasks.R' 90 | 'conversion-tasks-nm.R' 91 | 'description.R' 92 | 'issues.R' 93 | 'model-options.R' 94 | 'parameter-values.R' 95 | 'pk_component.R' 96 | 'test-helpers.R' 97 | 'util.R' 98 | 'variables.R' 99 | URL: https://github.com/UUPharmacometrics/assemblerr 100 | BugReports: https://github.com/UUPharmacometrics/assemblerr/issues 101 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | YEAR: 2019 2 | COPYRIGHT HOLDER: Sebastian Ueckert 3 | -------------------------------------------------------------------------------- /LICENSE.md: -------------------------------------------------------------------------------- 1 | # MIT License 2 | 3 | Copyright (c) 2019 Sebastian Ueckert 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /NAMESPACE: -------------------------------------------------------------------------------- 1 | # Generated by roxygen2: do not edit by hand 2 | 3 | S3method(format,assemblerr_declaration) 4 | S3method(format,assemblerr_statement) 5 | S3method(vec_proxy_compare,assemblerr_declaration) 6 | S3method(vec_proxy_equal,assemblerr_declaration) 7 | export("%>%") 8 | export(algebraic) 9 | export(assemblerr_options) 10 | export(check) 11 | export(cmp) 12 | export(compartment) 13 | export(dataset) 14 | export(declaration) 15 | export(facet_names_to_labels) 16 | export(flow) 17 | export(input_variable) 18 | export(interp) 19 | export(md_doc_links_for_package_functions) 20 | export(model) 21 | export(obs_additive) 22 | export(obs_combined) 23 | export(obs_proportional) 24 | export(pk_absorption_fo) 25 | export(pk_absorption_fo_lag) 26 | export(pk_absorption_fo_transit) 27 | export(pk_absorption_fo_zo) 28 | export(pk_absorption_zo) 29 | export(pk_absorption_zo_lag) 30 | export(pk_distribution_1cmp) 31 | export(pk_distribution_2cmp) 32 | export(pk_distribution_3cmp) 33 | export(pk_elimination_linear) 34 | export(pk_elimination_linear_nl) 35 | export(pk_elimination_nl) 36 | export(pk_model) 37 | export(prm_log_normal) 38 | export(prm_logit_normal) 39 | export(prm_no_var) 40 | export(prm_normal) 41 | export(render) 42 | export(tsk_estimation) 43 | export(tsk_output) 44 | export(tsk_output_xpose4) 45 | export(vars_data) 46 | export(vars_eta) 47 | export(vars_matches) 48 | export(vars_nm_std) 49 | export(vars_prms) 50 | export(vars_starts_with) 51 | import(vctrs) 52 | importFrom(cli,qty) 53 | importFrom(magrittr,"%>%") 54 | importFrom(methods,"slot<-") 55 | importFrom(methods,.valueClassTest) 56 | importFrom(methods,as) 57 | importFrom(methods,callNextMethod) 58 | importFrom(methods,getFunction) 59 | importFrom(methods,getSlots) 60 | importFrom(methods,is) 61 | importFrom(methods,new) 62 | importFrom(methods,show) 63 | importFrom(methods,slot) 64 | importFrom(methods,slotNames) 65 | importFrom(rlang,"%||%") 66 | importFrom(rlang,.data) 67 | importFrom(utils,lsf.str) 68 | importFrom(utils,read.csv) 69 | importFrom(utils,read.table) 70 | importFrom(utils,write.csv) 71 | -------------------------------------------------------------------------------- /NEWS.md: -------------------------------------------------------------------------------- 1 | # assemblerr 0.1.2 2 | * regenerate help files for compatability with new CRAN check 3 | 4 | # assemblerr 0.1.1 5 | * add CWRES to `vars_nm_std` 6 | * `pk_elimination_linear_nl` gains support for CLmm and Vmax parameterization 7 | 8 | # assemblerr 0.1.0 9 | * First release 10 | 11 | # assemblerr 0.0.0.9009 12 | * automatically rename variables with conflicting capitalization (e.g., emax and EMAX) 13 | * rename `pk_elimination_linear_mm()` to `pk_elimination_linear_nl()` 14 | * remove `pk_elimination_mm()` 15 | * extended help for PK component building blocks 16 | 17 | # assemblerr 0.0.0.9008 18 | * extended help for the building blocks: parameter, observation, compartment, flow 19 | * added pkgdown reference 20 | * added new "Getting started" vignette 21 | 22 | # assemblerr 0.0.0.9007 23 | * added `task` option to `render` function allowing to customize estimation and covariance records, e.g., `render(m, tasks = tsk_estimation(method = "foce"))` 24 | * added `tsk_ouput()` to specify variables that should be added to $TABLE 25 | 26 | # assemblerr 0.0.0.9006 27 | * RUV variance can be specified in the observation model `obs_additive(~conc, var_add = 2)` 28 | * default parameter values for PK components 29 | * parameter values can be defined when specifying parameters `prm_normal("k", mean = 1, var = 1)` 30 | * variables that are not defined in the model are automatically added as input variables 31 | * added warning when a new building block replaces an existing one 32 | 33 | # assemblerr 0.0.0.9005 34 | * added `pk_elimination_linear_mm` for mixed linear-mm elimination 35 | * models are now checked for issues before rendering 36 | * improved console printing of building blocks and models 37 | 38 | # assemblerr 0.0.0.9004 39 | * added `check()` function to check and list model issues 40 | * improved error checking and reporting when creating building blocks, e.g., `prm_normal()` 41 | * prediction declarations for observations do not longer need a left-hand side, e.g., `obs_additive(~C["central"])` is now valid. 42 | * `pk_elimination_mm` has been replaced with `pk_elimination_nl` to clarify that the default parameterization is not the classical MM model. Additionally, `pk_elimination_nl` allows selecting the classical parameterization using `pk_elimination_nl(prm_vmax = prm_log_normal("vmax"), prm_clmm = NULL)` 43 | * unsupported building blocks are now ignored with a warning when added to a model (e.g., `pk_model()+compartment('central')`) 44 | * option to include estimation & covariance step records in generated NONMEM model through `render(m, options = assemblerr_options(default_record.covariance_step = nm_covariance()))` 45 | * Added a `NEWS.md` file to track changes to the package. 46 | -------------------------------------------------------------------------------- /R/assemblerr-package.R: -------------------------------------------------------------------------------- 1 | #' @keywords internal 2 | #' @importFrom methods is getFunction 3 | #' @importFrom rlang .data %||% 4 | "_PACKAGE" 5 | 6 | #' Pipe operator 7 | #' 8 | #' See \code{magrittr::\link[magrittr]{\%>\%}} for details. 9 | #' 10 | #' @name %>% 11 | #' @rdname pipe 12 | #' @keywords internal 13 | #' @export 14 | #' @importFrom magrittr %>% 15 | #' @usage lhs \%>\% rhs 16 | NULL 17 | 18 | #' Internal vctrs methods 19 | #' 20 | #' @import vctrs 21 | #' @keywords internal 22 | #' @name assemblerr-vctrs 23 | NULL 24 | 25 | # The following block is used by usethis to automatically manage 26 | # roxygen namespace tags. Modify with care! 27 | ## usethis namespace: start 28 | ## usethis namespace: end 29 | NULL 30 | 31 | if(getRversion() >= "2.15.1") utils::globalVariables(".") 32 | -------------------------------------------------------------------------------- /R/ast.R: -------------------------------------------------------------------------------- 1 | #' Modify AST 2 | #' 3 | #' This recursive function is the work-horse for all expression transformations. It takes a language node and a transformer function, 4 | #' and applies the transformer recursivly to the node and all its child nodes. 5 | #' 6 | #' @param node A language node 7 | #' @param transformer A transformer function 8 | #' @param ... Additional arguments to the transformer function 9 | #' 10 | #' @return The transformed language node 11 | #' @keywords internal 12 | transform_ast <- function(node, transformer, ...){ 13 | if(rlang::is_atomic(node) || rlang::is_symbol(node)) return(transformer(node, ...)) 14 | else if(rlang::is_call(node)){ 15 | node <- transformer(node, ...) 16 | if(rlang::is_call(node)) for(i in 1:length(node)) node[[i]] <- transform_ast(node[[i]], transformer, ...) 17 | return(node) 18 | }else if(rlang::is_pairlist(node)){ 19 | lapply(node, transform_ast, ...) %>% 20 | as.pairlist() %>% 21 | return() 22 | }else if(is.null(node)){ 23 | return(node) 24 | } else { 25 | stop("Don't know how to handle type ", typeof(node), 26 | call. = FALSE) 27 | } 28 | } 29 | 30 | 31 | substitution_transformer <- function(node, substitutions){ 32 | if (exists(deparse(node, width.cutoff = 500L), substitutions)) { 33 | node <- substitutions[[deparse(node)]] 34 | } 35 | node 36 | } 37 | 38 | index_transformer <- function(node, array_name, substitutions){ 39 | # if vector access 40 | if(rlang::is_call(node) && rlang::call_name(node) == "[" && node[[2]] == rlang::sym(array_name)){ 41 | if(!exists(node[[3]], substitutions)) rlang::warn("missing_substitution", index = node[[3]]) 42 | node[[3]] <- substitutions[[node[[3]]]] 43 | } 44 | node 45 | } 46 | 47 | remove_array_transformer <- function(node) { 48 | if (expr_is_arr(node)){ 49 | node <- node[[2]] 50 | } 51 | node 52 | } 53 | 54 | expr_is_arr <- function(node) { 55 | rlang::is_call(node) && rlang::call_name(node) == "[" 56 | } 57 | -------------------------------------------------------------------------------- /R/conversion-input_variable-nm.R: -------------------------------------------------------------------------------- 1 | #' @include input_variable.R 2 | #' @include nm_model.R 3 | #' @include model.R 4 | 5 | setMethod( 6 | f = "convert", 7 | signature = c(target = "NmModel", source = "Model", component = "InputVariable"), 8 | definition = function(target, source, component, options) { 9 | target + nm_input(name = component@name) 10 | } 11 | ) 12 | -------------------------------------------------------------------------------- /R/conversion-meta-nm.R: -------------------------------------------------------------------------------- 1 | #' @include meta.R 2 | #' @include model.R 3 | #' @include nm_model.R 4 | 5 | 6 | setMethod( 7 | f = "convert", 8 | signature = c(target = "NmModel", source = "Model", component = "Metadata"), 9 | definition = function(target, source, component, options) { 10 | if (component@name == "dataset") { 11 | target <- target + nm_data(path = component@value) 12 | } 13 | target 14 | } 15 | ) 16 | -------------------------------------------------------------------------------- /R/conversion-nm.R: -------------------------------------------------------------------------------- 1 | 2 | 3 | setMethod( 4 | f = "convert", 5 | signature = c(target = "NmModel", source = "Model", component = "missing"), 6 | definition = function(target, source, component, options) { 7 | source <- optimize_for_conversion(source, target, options = options) 8 | target <- convert(target, source, source@facets[["ParameterFacet"]], options) %>% 9 | convert(source, source@facets[["CompartmentFacet"]], options) %>% 10 | convert(source, source@facets[["FlowFacet"]], options) %>% 11 | convert(source, source@facets[["AlgebraicFacet"]], options) %>% 12 | convert(source, source@facets[["ObservationFacet"]], options) %>% 13 | convert(source, source@facets[["InputVariableFacet"]], options) %>% 14 | convert(source, source@facets[["MetadataFacet"]], options) 15 | # target <- target + options[["default_record.covariance_step"]] 16 | # target <- target + options[["default_record.estimation_step"]] 17 | if (vec_is_empty(source@facets[["InputVariableFacet"]]@entries)) { 18 | target <- target + 19 | nm_input("id", "id") + 20 | nm_input("time", "time") + 21 | nm_input("dv", "dv") + 22 | nm_input("amt", "amt") 23 | } else { 24 | if (!"id" %in% names(source@facets[["InputVariableFacet"]]@entries)) { 25 | target <- target + 26 | nm_input("id", "id") 27 | } 28 | if (!"dv" %in% names(source@facets[["InputVariableFacet"]]@entries)) { 29 | target <- target + 30 | nm_input("dv", "dv") 31 | } 32 | } 33 | target 34 | } 35 | ) 36 | -------------------------------------------------------------------------------- /R/conversion-observation-nm.R: -------------------------------------------------------------------------------- 1 | #' @include observation.R 2 | 3 | setMethod( 4 | f = "convert", 5 | signature = c(target = "NmModel", source = "ANY", component = "ObsNormalCombined"), 6 | definition = function(target, source, component, options) { 7 | ruv_add_dcl <- declaration(~0) 8 | ruv_prop_dcl <- declaration(~0) 9 | values <- parameter_values(component) 10 | if (component@additive_term) { 11 | target <- target + nm_sigma("add", initial = values["var_add"]) 12 | eps_index <- index_of(target@facets$NmSigmaParameterFacet, "add") 13 | ruv_add_dcl <- dcl_substitute(declaration(~eps[i]), c(i = eps_index)) 14 | } 15 | if (component@proportional_term) { 16 | target <- target + nm_sigma("prop", initial = values["var_prop"]) 17 | eps_index <- index_of(target@facets$NmSigmaParameterFacet, "prop") 18 | ruv_prop_dcl <- dcl_substitute(declaration(~f*eps[i]), c(i = eps_index)) 19 | } 20 | ipred_dcl <- component@prediction 21 | if (vec_size(source@facets$CompartmentFacet@entries) > 0) { 22 | ipred_dcl <- replace_compartment_references(ipred_dcl, target, source) 23 | } 24 | f <- dcl_id(ipred_dcl) 25 | if (is.null(f[[1]])) { 26 | f <- dcl_def(ipred_dcl) 27 | ipred_dcl <- NULL 28 | } 29 | ruv_dcl <- vec_c(declaration(y~f), ruv_add_dcl, ruv_prop_dcl) %>% 30 | dcl_sum() %>% 31 | dcl_substitute( 32 | list( 33 | f = f 34 | ) 35 | ) 36 | d <- vec_c(ipred_dcl, 37 | ruv_dcl) 38 | target <- target + nm_error(statement = as_statement(d)) 39 | target 40 | } 41 | ) 42 | 43 | 44 | replace_compartment_references <- function(dcl, target, source){ 45 | if (any(c("C","A","dadt") %in% dcl_vars_chr(dcl))) { 46 | conc_dcls <- as.list(generate_concentration_substitutions(source@facets[["CompartmentFacet"]]@entries)) 47 | compartment_indicies <- name_index_map(target@facets$NmCompartmentFacet) 48 | dcl <- dcl %>% 49 | dcl_substitute(substitutions = conc_dcls) %>% 50 | dcl_substitute_index("A", compartment_indicies) %>% 51 | dcl_substitute_index("dadt", compartment_indicies) 52 | } 53 | return(dcl) 54 | } 55 | 56 | 57 | generate_concentration_substitutions <- function(cmps){ 58 | names <- names(cmps) 59 | volume <- vec_c(!!!unname(purrr::map(cmps, "volume"))) 60 | d <- dcl_substitute(declaration(C[name]~A[name]), 61 | substitutions = list(name = names)) 62 | dcl_devide(d, volume) 63 | } 64 | 65 | -------------------------------------------------------------------------------- /R/conversion-parameter-nm.R: -------------------------------------------------------------------------------- 1 | #' @include parameter.R 2 | 3 | 4 | # log-normal -------------------------------------------------------------- 5 | 6 | 7 | setMethod( 8 | f = "convert", 9 | signature = c(target = "NmModel", source = "ANY", component = "PrmLogNormal"), 10 | definition = function(target, source, component, options) { 11 | values <- parameter_values(component) 12 | target <- target + 13 | nm_theta(component@name, initial = values["median"], lbound = 0) + 14 | nm_omega(component@name, initial = values["var_log"]) 15 | 16 | theta_index <- index_of(target@facets$NmThetaParameterFacet, component@name) 17 | eta_index <- index_of(target@facets$NmOmegaParameterFacet, component@name) 18 | 19 | if (options$prm.use_mu_referencing) { 20 | mu_name <- paste0('mu_',eta_index) 21 | stm <- statement( 22 | "{mu_name} <- log(theta[{theta_index}])", 23 | "{component@name} <- exp({mu_name} + eta[{eta_index}])" 24 | ) 25 | } else { 26 | stm <- statement( 27 | "{component@name} <- theta[{theta_index}]*exp(eta[{eta_index}])" 28 | ) 29 | } 30 | target + nm_pk(stm) 31 | } 32 | ) 33 | 34 | 35 | # normal ------------------------------------------------------------------ 36 | 37 | 38 | 39 | setMethod( 40 | f = "convert", 41 | signature = c(target = "NmModel", source = "ANY", component = "PrmNormal"), 42 | definition = function(target, source, component, options) { 43 | values <- parameter_values(component) 44 | target <- target + 45 | nm_theta(component@name, initial = values["mean"], lbound = 0) + 46 | nm_omega(component@name, initial = values["var"]) 47 | 48 | theta_index <- index_of(target@facets$NmThetaParameterFacet, component@name) 49 | eta_index <- index_of(target@facets$NmOmegaParameterFacet, component@name) 50 | if (options$prm.use_mu_referencing) { 51 | mu_name <- sym(paste0("mu_",eta_index)) 52 | stm <- statement( 53 | "{mu_name} <- theta[{theta_index}]", 54 | "{component@name} <- {mu_name} + eta[{eta_index}]" 55 | ) 56 | } else { 57 | stm <- statement( 58 | "{component@name} <- theta[{theta_index}] + eta[{eta_index}]" 59 | ) 60 | } 61 | target + nm_pk(stm) 62 | } 63 | ) 64 | 65 | # logit ------------------------------------------------------------------ 66 | 67 | 68 | 69 | setMethod( 70 | f = "convert", 71 | signature = c(target = "NmModel", source = "ANY", component = "PrmLogitNormal"), 72 | definition = function(target, source, component, options) { 73 | values <- parameter_values(component) 74 | target <- target + 75 | nm_theta(component@name, initial = values["mean_logit"], lbound = 0, ubound = 1) + 76 | nm_omega(component@name, initial = values["var_logit"]) 77 | 78 | theta_index <- index_of(target@facets$NmThetaParameterFacet, component@name) 79 | eta_index <- index_of(target@facets$NmOmegaParameterFacet, component@name) 80 | prm_logit <- paste0("logit_", component@name) 81 | prm <- component@name 82 | if (options$prm.use_mu_referencing) { 83 | mu_name <- paste0('mu_',eta_index) 84 | stm <- statement( 85 | "{mu_name} <- log(theta[{theta_index}])/(1 - log(theta[{theta_index}]))", 86 | "{prm_logit} <- {mu_name} + eta[{eta_index}]", 87 | "{prm} <- exp({prm_logit})/(1 + exp({prm_logit}))" 88 | ) 89 | } else { 90 | stm <- statement( 91 | "{prm_logit} <- log(theta[{theta_index}]/(1 - theta[{theta_index}])) + eta[{eta_index}]", 92 | "{prm} <- exp({prm_logit})/(1 + exp({prm_logit}))" 93 | ) 94 | } 95 | target + nm_pk(stm) 96 | } 97 | ) 98 | 99 | 100 | # no-var -------------------------------------------------------------- 101 | 102 | 103 | setMethod( 104 | f = "convert", 105 | signature = c(target = "NmModel", source = "ANY", component = "PrmNoVar"), 106 | definition = function(target, source, component, options) { 107 | values <- parameter_values(component) 108 | target <- target + 109 | nm_theta(component@name, initial = values["value"], lbound = 0) 110 | 111 | theta_index <- index_of(target@facets$NmThetaParameterFacet, component@name) 112 | 113 | target + 114 | nm_pk( 115 | statement( 116 | "{component@name} <- theta[{theta_index}]" 117 | ) 118 | ) 119 | } 120 | ) 121 | -------------------------------------------------------------------------------- /R/conversion-tasks-nm.R: -------------------------------------------------------------------------------- 1 | #' @include tasks.R 2 | 3 | 4 | setMethod( 5 | f = "convert", 6 | signature = c(target = "NmModel", source = "GenericModel", component = "ModelingTasks"), 7 | definition = function(target, source, component, options) { 8 | purrr::reduce( 9 | .init = target, 10 | .x = component, 11 | .f = ~convert(.x, source, .y, options) 12 | ) 13 | } 14 | ) 15 | 16 | 17 | setMethod( 18 | f = "convert", 19 | signature = c(target = "NmModel", source = "GenericModel", component = "EstimationTask"), 20 | definition = function(target, source, component, options) { 21 | method <- switch( 22 | component@algorithm, 23 | foce = "cond", 24 | `foce-inter` = "cond", 25 | `foce-no-inter` = "cond", 26 | `fo` = "0", 27 | `imp` = "imp", 28 | `saem` = "saem" 29 | ) 30 | if (component@algorithm == "foce") { 31 | interaction <- source@facets$ObservationFacet@entries[[1]]@proportional_term 32 | } else { 33 | interaction <- component@algorithm == "foce-inter" 34 | } 35 | if (method %in% c("cond", "0")) { 36 | maxeval <- 999999L 37 | } else { 38 | maxeval <- NA_integer_ 39 | } 40 | if (method %in% c("imp", "saem")) { 41 | auto <- TRUE 42 | } else { 43 | auto <- NA 44 | } 45 | cov_step <- NULL 46 | if (component@standard_errors && length(target@facets$NmCovarianceStepFacet@entries) == 0) { 47 | cov_step <- nm_covariance() 48 | } 49 | target + 50 | nm_estimation( 51 | method = method, 52 | interaction = interaction, 53 | maxeval = maxeval, 54 | auto = auto, 55 | target_options = component@target_options 56 | ) + 57 | cov_step 58 | } 59 | ) 60 | 61 | 62 | setMethod( 63 | f = "convert", 64 | signature = c(target = "NmModel", source = "GenericModel", component = "OutputTask"), 65 | definition = function(target, source, component, options) { 66 | available_variables <- c( 67 | defined_variables(source), 68 | defined_variables(target) 69 | ) 70 | selected_variables <- select_variables(available_variables, !!component@selector) 71 | target + 72 | nm_table( 73 | filename = component@filename, 74 | items = names(selected_variables) 75 | ) 76 | } 77 | ) 78 | -------------------------------------------------------------------------------- /R/conversion.R: -------------------------------------------------------------------------------- 1 | #' @include model.R 2 | #' @include pk_model.R 3 | #' @include facet.R 4 | 5 | 6 | setGeneric(name = "convert", 7 | def = function(target, source, component, options) standardGeneric("convert")) 8 | 9 | setMethod( 10 | f = "convert", 11 | signature = c(target = "ANY", source = "GenericModel", component = "missing"), 12 | definition = function(target, source, component, options) { 13 | convert(model(), source, options = options) %>% 14 | convert(target = target, source = ., options = options) 15 | } 16 | ) 17 | 18 | 19 | setMethod( 20 | f = "convert", 21 | signature = c(target = "ANY", source = "ANY", component = "Facet"), 22 | definition = function(target, source, component, options) { 23 | purrr::reduce(component@entries, ~convert(target = .x, source = source, component = .y, options = options), .init = target) 24 | } 25 | ) 26 | -------------------------------------------------------------------------------- /R/declaration-creation.R: -------------------------------------------------------------------------------- 1 | 2 | #' `declaration` constructor 3 | #' 4 | #' The internal constructor for a declaration vector. The user-facing version is `declaration`. 5 | #' 6 | #' The arguments `identifier` and `definition` are lists of R expressions. For `identifier` only symbols, array expressions 7 | #' (e.g., theta[1]), or NULL are permitted. 8 | #' 9 | #' @param identifier List of expressions 10 | #' @param definition List of expressions 11 | #' 12 | #' @return An assemblerr_declaration object 13 | #' @keywords internal 14 | new_declaration <- function(identifier = list(), definition = list()){ 15 | vctrs::vec_assert(identifier, ptype = list()) 16 | vctrs::vec_assert(definition, ptype = list()) 17 | identifier <- rlang::set_names(identifier, NULL) 18 | definition <- rlang::set_names(definition, NULL) 19 | if (!rlang::is_empty(definition) && all(!purrr::map_lgl(definition, rlang::is_expression))) 20 | rlang::abort(message = "`definition` must be an expression") 21 | if (!rlang::is_empty(identifier) && all(!purrr::map_lgl(identifier, rlang::is_expression))) 22 | rlang::abort(message = "`identifier` must be an expression") 23 | if (!all(purrr::map_lgl(identifier, is_valid_lhs))) 24 | rlang::abort("The identifiers need to be symbols or array expressions") 25 | vctrs::new_rcrd(list(identifier = identifier, definition = definition), 26 | class = "assemblerr_declaration") 27 | } 28 | 29 | setOldClass("assemblerr_declaration") 30 | 31 | 32 | #' Declaration 33 | #' 34 | #' A declaration is the mathematical definition of a set of variables. It is the lowest level building block for a model 35 | #' in `assemblerr`. A declaration consists of the variable names being declared (the identifiers) and their definition. The 36 | #' `declaration` function allows the specification of a declaration using `R` formulae. 37 | #' 38 | #' @param ... List of R formulae with a single symbol on the left-hand side and a valid R expression on the right 39 | #' 40 | #' @return A declaration vector 41 | #' @export 42 | #' 43 | #' @keywords internal 44 | #' 45 | #' @examples 46 | #' d <- declaration(cl~theta[1]+eta[1]) 47 | #' d2 <- declaration(v=theta[2]*exp(eta[2])) 48 | declaration <- function(...){ 49 | dots <- rlang::exprs(...) 50 | lhs <- purrr::map_if(dots, rlang::is_formula, rlang::f_lhs, .else = ~NULL) 51 | new_identifier <- purrr::imap(lhs, function(x, y) { 52 | if (is.null(x)) { 53 | if (y == "") { 54 | NULL 55 | }else{ 56 | rlang::sym(y) 57 | } 58 | }else{ 59 | x 60 | } 61 | }) 62 | if (!all(purrr::map_lgl(new_identifier, is_valid_lhs))) 63 | rlang::abort("The left-hand side of each formula needs to be a symbol or an array expression") 64 | definition <- purrr::map_if(dots, rlang::is_formula, rlang::f_rhs) 65 | return(new_declaration(new_identifier, definition)) 66 | } 67 | 68 | 69 | 70 | is_declaration <- function(x) { 71 | return(inherits(x, "assemblerr_declaration")) 72 | } 73 | 74 | 75 | as_declaration <- function(x) UseMethod("as_declaration") 76 | 77 | as_declaration.assemblerr_declaration <- function(x) x 78 | 79 | as_declaration.formula <- function(x) declaration(!!x) 80 | 81 | as_declaration.numeric <- function(x) new_declaration(vec_rep(list(NULL), vec_size(x)), definition = as.list(x)) 82 | 83 | as_declaration.character <- function(x) { 84 | if (!all(is_valid_variable_name(x))) rlang::abort("Invalid variable name") 85 | new_declaration(vec_rep(list(NULL), vec_size(x)), rlang::syms(x)) 86 | } 87 | 88 | as_declaration.name <- function(x) new_declaration(list(NULL), list(x)) 89 | 90 | # user-facing version with informative error message 91 | ui_as_declaration <- function(x, error_call) { 92 | withCallingHandlers( 93 | as_declaration(x), 94 | error = function(cnd) rlang::abort( 95 | c( 96 | "Invalid declaration", 97 | x = paste0("'", rlang::as_label(rlang::enexpr(x)), "' can not be interpreted as a declaration."), 98 | i = "A declaration can be specified as a formula, number or the name of a variable." 99 | ), 100 | call = error_call, 101 | parent = cnd, 102 | use_cli_format = TRUE 103 | ) 104 | ) 105 | } 106 | 107 | 108 | as.list.assemblerr_declaration <- function(x, ...) { 109 | lbls <- purrr::map_if(dcl_id(x), ~!is.null(.x), deparse, .else = ~"") 110 | rlang::set_names(dcl_def(x), lbls) 111 | } 112 | -------------------------------------------------------------------------------- /R/description.R: -------------------------------------------------------------------------------- 1 | TreeDescription <- setClass("TreeDescription", 2 | contains = "character", 3 | slots = c(children = "list")) 4 | 5 | setMethod(f = "initialize", 6 | signature = "TreeDescription", 7 | definition = function(.Object, description = character(), children = NULL){ 8 | .Object <- callNextMethod(.Object, 9 | description) 10 | .Object@children <- purrr::map(children, as, "TreeDescription") 11 | .Object 12 | }) 13 | 14 | setMethod(f = "show", 15 | signature = "TreeDescription", 16 | definition = function(object) { 17 | show_levels <- function(tree, level = 0) { 18 | tabs <- strrep("\t", level) 19 | cat(paste0(tabs, tree, "\n")) 20 | purrr::walk(tree@children, show_levels, level = level + 1) 21 | } 22 | show_levels(object) 23 | }) 24 | 25 | print_tdesc_as_tree <- function(tree_description) { 26 | flatten_tree <- function(tree) { 27 | if (rlang::is_empty(tree@children)) return(data_frame(parent = as.character(tree), children = list(character()))) 28 | own <- data_frame(parent = as.character(tree), children = list(purrr::map_chr(tree@children, as.character))) 29 | children <- purrr::map(unname(tree@children), flatten_tree) 30 | return(vec_c(own, !!!children)) 31 | } 32 | flatten_tree(tree_description) %>% 33 | cli::tree() %>% 34 | print() 35 | } 36 | 37 | print_tdesc_as_list <- function(tree_description) { 38 | print_recursive <- function(tree) { 39 | outer <- cli::cli_ul() 40 | purrr::walk(tree@children, function(x){ 41 | cli::cli_li(x) 42 | print_recursive(x) 43 | }) 44 | cli::cli_end(outer) 45 | } 46 | cli::cli_text(tree_description) 47 | print_recursive(tree_description) 48 | } 49 | 50 | print_tdesc_as_simple_list <- function(tree_description, skip_root = FALSE) { 51 | format_recursive <- function(tree, level = 0) { 52 | tabs <- strrep(" ", level) 53 | str <- character() 54 | if (skip_root && level == 0) { 55 | root <- character() 56 | } else { 57 | root <- paste0(tabs, tree) 58 | } 59 | vec_c( 60 | root, 61 | purrr::map(tree@children, format_recursive, level = level + 1) %>% purrr::flatten_chr() 62 | ) 63 | } 64 | cli::cat_line(format_recursive(tree_description)) 65 | } 66 | 67 | print_type_header <- function(type) { 68 | cat( 69 | cli::style_italic( 70 | cli::col_grey("# an assemblerr ",type) 71 | ), 72 | "\n") 73 | } 74 | 75 | #' Print tree description in compact format 76 | #' 77 | #' @param tree_description A TreeDescription object 78 | #' @param type type label to print to console 79 | #' @param show which child nodes of the root to print or 'all' to print all 80 | #' @param child_type type label for child elements 81 | #' @param skip_root whether the root node should be printed 82 | #' 83 | #' @importFrom methods as 84 | #' 85 | #' @return The function prints to the console 86 | #' @keywords internal 87 | print_shortened_tree_description <- function(tree_description, 88 | type = "building block", 89 | show = 'all', 90 | child_type = "entries", 91 | skip_root = TRUE) { 92 | print_type_header(type) 93 | tree_description <- as(tree_description, "TreeDescription") 94 | n_before <- length(tree_description@children) 95 | if (show[1] != "all") { 96 | tree_description@children[!names(tree_description@children) %in% show] <- NULL 97 | } 98 | n_after <- length(tree_description@children) 99 | print_tdesc_as_simple_list(tree_description, skip_root = skip_root) 100 | if (n_before != n_after) { 101 | cat( 102 | cli::style_italic( 103 | cli::col_grey(interp("# ...{n_before - n_after} more ", child_type)) 104 | ), 105 | "\n") 106 | } 107 | } 108 | 109 | print_issues_warning <- function(issues) { 110 | n_critical <- length(purrr::keep(issues, ~is(.x, "CriticalIssue"))) 111 | if (n_critical > 0) { 112 | cat( 113 | cli::style_italic( 114 | cli::col_red( 115 | cli::pluralize("! {n_critical} critical issue{?s}") 116 | ) 117 | ), 118 | "\n") 119 | } 120 | } 121 | 122 | 123 | describe <- function(x) { 124 | description(x) %>% 125 | print_tdesc_as_tree() 126 | } 127 | 128 | -------------------------------------------------------------------------------- /R/generics.R: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UUPharmacometrics/assemblerr/00f8b410470d12bca39445f7186449c820e18177/R/generics.R -------------------------------------------------------------------------------- /R/input_variable.R: -------------------------------------------------------------------------------- 1 | #' @include facet.R 2 | #' @include nm_model.R 3 | #' @include model.R 4 | #' 5 | InputVariable <- setClass( 6 | "InputVariable", 7 | contains = "NamedFacetEntry", 8 | prototype = prototype(facet_class = "InputVariableFacet") 9 | ) 10 | 11 | InputVariableFacet <- setClass( 12 | "InputVariableFacet", 13 | contains = "NamedFacet", 14 | prototype = prototype(entry_class = "InputVariable", 15 | label = "input variables") 16 | ) 17 | 18 | setMethod( 19 | f = "defined_variables", 20 | signature = "InputVariableFacet", 21 | definition = function(x) { 22 | purrr::map(x@entries, ~DataDefinedVariable(.x@name)) %>% 23 | purrr::reduce(.init = VariableList(), .f = combine) 24 | } 25 | ) 26 | 27 | setMethod( 28 | f = "rename_variables", 29 | signature = "InputVariableFacet", 30 | definition = function(x, variable_mapping) { 31 | for (i in seq_along(x@entries)) { 32 | if (x@entries[[i]]@name %in% names(variable_mapping)) { 33 | x@entries[[i]]@name <- variable_mapping[x@entries[[i]]@name] 34 | } 35 | } 36 | names(x@entries) <- names(x) 37 | return(x) 38 | } 39 | ) 40 | 41 | #' Input variables 42 | #' 43 | #' These building block declare input variables, i.e., variables that are defined in the dataset. 44 | #' 45 | #' An input variable is defined in the dataset and is declared so that it can be used in the rest of the model definition. The function 46 | #' `input_variable()` declares a single variable whereas the `dataset()` function reads the header of the file provided and 47 | #' declares all variables found. 48 | #' 49 | #' @param name Variable name 50 | #' 51 | #' @return A building block of type 'input_variable' 52 | #' 53 | #' @export 54 | #' @examples 55 | #' m <- model() + 56 | #' input_variable("dose") + 57 | #' prm_log_normal("emax") + 58 | #' prm_log_normal("ed50") + 59 | #' obs_additive(eff~emax*dose/(ed50+dose)) 60 | #' render(m) 61 | #' @md 62 | #' @rdname input_variables 63 | input_variable <- function(name){ 64 | if (!is.character(name)) stop("'name' needs to be a character vector") 65 | InputVariable(name = name) 66 | } 67 | 68 | #' @param path Dataset path 69 | #' @param use_only_filename Whether to include the path of the file 70 | #' @importFrom utils read.csv 71 | #' @importFrom utils read.table 72 | #' @export 73 | #' @rdname input_variables 74 | dataset <- function(path, use_only_filename = FALSE){ 75 | if (grepl(".csv$",path)) { 76 | tab <- read.csv(path, header = TRUE, nrows = 1, check.names = FALSE) 77 | }else{ 78 | tab <- read.table(path, header = TRUE, nrows = 1, check.names = FALSE) 79 | } 80 | col_names <- colnames(tab) %>% 81 | gsub("[^[:alnum:] ]", "", .) 82 | if (any(duplicated(col_names))) { 83 | duplicated_names <- col_names[duplicated(col_names)] %>% 84 | unique() 85 | rlang::warn( 86 | c("Duplicated column names", 87 | i = cli::pluralize("The column name{?s} {duplicated_names} appeared multiple times and {?was/were} adjusted.") 88 | ) 89 | ) 90 | col_names <- make.unique(col_names, "_") 91 | } 92 | if (use_only_filename) path <- basename(path) 93 | purrr::map(tolower(col_names), input_variable) %>% 94 | purrr::reduce(`+`) + 95 | metadata("dataset", path) 96 | } 97 | 98 | 99 | add_missing_variables <- function(model, issues, warn = TRUE) { 100 | variables <- purrr::keep(issues, ~is(.x, "MissingVariableIssue")) %>% 101 | purrr::map(~.x@variables) %>% 102 | purrr::flatten_chr() 103 | if (warn) { 104 | rlang::warn( 105 | c( 106 | "Undefined variables added", 107 | x = interp("The variable{?s} {sq(variables)} {?was/were} not defined and {?has/have} been added as input variable{?s}.") 108 | ) 109 | ) 110 | } 111 | variables %>% 112 | purrr::map(input_variable) %>% 113 | purrr::reduce(`+`, .init = model) 114 | } 115 | -------------------------------------------------------------------------------- /R/meta.R: -------------------------------------------------------------------------------- 1 | #' @include facet.R 2 | #' @include nm_model.R 3 | #' @include model.R 4 | #' 5 | Metadata <- setClass( 6 | "Metadata", 7 | slots = c(value = "character"), 8 | contains = "NamedFacetEntry", 9 | prototype = prototype(facet_class = "MetadataFacet") 10 | ) 11 | 12 | MetadataFacet <- setClass( 13 | "MetadataFacet", 14 | contains = "NamedFacet", 15 | prototype = prototype(entry_class = "Metadata") 16 | ) 17 | 18 | 19 | 20 | metadata <- function(name, value){ 21 | if (!is.character(name)) stop("'name' needs to be a character vector") 22 | Metadata(name = name, value = value) 23 | } 24 | 25 | -------------------------------------------------------------------------------- /R/model-options.R: -------------------------------------------------------------------------------- 1 | 2 | #' Options 3 | #' 4 | #' This function creates a list of options for the use with the render function. 5 | #' 6 | #' The function helps to create properly formatted list that can serve as input to the `options=` argument 7 | #' of the `render()` function. 8 | #' 9 | #' @param prm.use_mu_referencing Use mu-referencing? 10 | #' @param ode.use_special_advans Use analytic solution ADVANs? 11 | #' @param ode.use_general_linear_advans Use ADVANs for linear ODEs? 12 | #' @param ode.general_nonlinear_advan ADVAN to be used for non-linear ODEs 13 | #' @param ode.general_linear_advan ADVAN to be used for linear ODEs 14 | #' @param ode.preferred_trans_routines Order of TRANS routines to be tried 15 | #' @param issues.missing_variables How to handle missing variables 16 | #' 17 | #' @return A list of options 18 | #' 19 | #' @md 20 | #' @export 21 | assemblerr_options <- function(prm.use_mu_referencing = FALSE, 22 | ode.use_special_advans = TRUE, 23 | ode.use_general_linear_advans = TRUE, 24 | ode.general_nonlinear_advan = "advan13", 25 | ode.general_linear_advan = "advan5", 26 | ode.preferred_trans_routines = c("trans2", "trans4"), 27 | issues.missing_variables = c("fix-warn", "fix", "ignore", "fail")) { 28 | # TODO: add 'warn' option for issues.missing_variables 29 | return( 30 | list( 31 | prm.use_mu_referencing = prm.use_mu_referencing, 32 | ode.use_special_advans = ode.use_special_advans, 33 | ode.use_general_linear_advans = ode.use_general_linear_advans, 34 | ode.general_nonlinear_advan = ode.general_nonlinear_advan, 35 | ode.general_linear_advan = ode.general_linear_advan, 36 | ode.preferred_trans_routines = ode.preferred_trans_routines, 37 | issues.missing_variables = match.arg(issues.missing_variables) 38 | ) 39 | ) 40 | } 41 | -------------------------------------------------------------------------------- /R/model.R: -------------------------------------------------------------------------------- 1 | #' @include facet.R 2 | #' @include conversion.R 3 | Model <- setClass("Model", contains = "GenericModel") 4 | 5 | setMethod( 6 | f = "initialize", 7 | signature = "Model", 8 | definition = function(.Object, ...) { 9 | callNextMethod(.Object, 10 | facets = list(ParameterFacet(), 11 | AlgebraicFacet(), 12 | CompartmentFacet(), 13 | FlowFacet(), 14 | ObservationFacet(), 15 | InputVariableFacet(), 16 | MetadataFacet()), 17 | ...) 18 | } 19 | ) 20 | 21 | setMethod( 22 | f = "show", 23 | signature = "Model", 24 | definition = function(object) { 25 | print_shortened_tree_description( 26 | tree_description = compact_description(object), 27 | type = "model", 28 | child_type = "facet{?s}", 29 | show = c("ParameterFacet", "AlgebraicFacet", "CompartmentFacet", "FlowFacet", "ObservationFacet") 30 | ) 31 | print_issues_warning(check_component(object)) 32 | } 33 | ) 34 | 35 | 36 | 37 | 38 | setMethod( 39 | f = "convert", 40 | signature = c(target = "Model", source = "Model", component = "missing"), 41 | definition = function(target, source, component, options) { 42 | source 43 | } 44 | ) 45 | 46 | #' General model 47 | #' 48 | #' This function creates the basis for a general pharmacometric model, a flexible but verbose model type. 49 | #' 50 | #' The function creates the foundation for a general pharmacometric model to which different building blocks can be added. The following building 51 | #' blocks are relevant for this model type: 52 | #' * Parameters: `r md_doc_links_for_package_functions("^prm_")` 53 | #' * Observations: `r md_doc_links_for_package_functions("^obs_")` 54 | #' * Algebraic relationships: [algebraic] 55 | #' * Compartments: [compartment] 56 | #' * Flows: [flow] 57 | #' * Input variables: [input_variable], [dataset] 58 | #' 59 | #' The more specialized [pk_model()] is converted to a general model during the rendering process. 60 | #' 61 | #' @return A general pharmacometric model 62 | #' @export 63 | #' @examples 64 | #' m <- model() + 65 | #' input_variable("dose") + 66 | #' prm_log_normal("emax") + 67 | #' prm_log_normal("ed50") + 68 | #' obs_additive(eff~emax*dose/(ed50+dose)) 69 | #' render(m) 70 | #' @md 71 | model <- function(){ 72 | Model() 73 | } 74 | 75 | setOldClass("model") 76 | 77 | setMethod( 78 | f = "check_component", 79 | signature = signature(x = "Model"), 80 | definition = function(x, ...) { 81 | issues <- c(IssueList(), 82 | callNextMethod(x)) 83 | return(issues) 84 | } 85 | ) 86 | 87 | 88 | 89 | check_for_undefined_variables <- function(dcls, defined_vars, facet_label) { 90 | required_vars <- dcl_external_variables(dcls) %>% 91 | as.character() 92 | missing_vars <- setdiff(required_vars, names(defined_vars)) 93 | if (!vec_is_empty(missing_vars)) { 94 | return( 95 | MissingVariableIssue(interp("Undefined {qty(length(missing_vars))}variable{?s} {sq(missing_vars)} in {facet_label}"), variables = missing_vars) 96 | ) 97 | } else{ 98 | return(NULL) 99 | } 100 | } 101 | 102 | collect_defined_variables <- function(model, facets, additional_variables = list()) { 103 | existing_facets <- facets[facets %in% names(model@facets)] 104 | purrr::map(model@facets[existing_facets], defined_variables) %>% 105 | purrr::reduce(.init = VariableList(), combine) %>% 106 | c(additional_variables) 107 | } 108 | -------------------------------------------------------------------------------- /R/node-classes.R: -------------------------------------------------------------------------------- 1 | #' @importFrom methods new 2 | #' @importFrom methods show 3 | #' @importFrom methods callNextMethod 4 | #' @importFrom methods getSlots 5 | 6 | # TODO: Need to implement fragment as a node list accepting everything 7 | 8 | 9 | 10 | Node <- setClass("Node") 11 | 12 | setIs("Node", "BuildingBlock") 13 | 14 | setMethod( 15 | f = "combine", 16 | signature = signature(x = "Node"), 17 | definition = function(x, y) { 18 | slots <- getSlots(class(x)) 19 | for (s in names(slots)) { 20 | if (is(y, class(slot(x, s)))) { 21 | slot(x, s) <- y 22 | break 23 | } else if (is(slot(x, s), "NodeList")) { 24 | slot(x, s) <- combine(slot(x, s), y) 25 | break 26 | } 27 | } 28 | return(x) 29 | } 30 | ) 31 | 32 | setMethod( 33 | f = "description", 34 | signature = "Node", 35 | definition = function(x) { 36 | class(x) 37 | } 38 | ) 39 | 40 | NamedNode <- setClass( 41 | "NamedNode", 42 | contains = "Node", 43 | slots = c(name = "character") 44 | ) 45 | 46 | 47 | 48 | NodeList <- setClass("NodeList", 49 | contains = "list", 50 | slots = c(node_class = "character"), 51 | prototype = prototype(node_class = "Node")) 52 | 53 | setMethod( 54 | f = "initialize", 55 | signature = "NodeList", 56 | definition = function(.Object, ...){ 57 | dots <- rlang::list2(...) 58 | callNextMethod(.Object, dots) 59 | } 60 | ) 61 | 62 | setIs("NodeList", "BuildingBlock") 63 | 64 | setMethod( 65 | f = "combine", 66 | signature = signature(x = "NodeList", y = "Node"), 67 | definition = function(x, y) { 68 | if (is(y, x@node_class)) { 69 | x@.Data <- append(x@.Data, y) 70 | } 71 | return(x) 72 | } 73 | ) 74 | 75 | setMethod( 76 | f = "combine", 77 | signature = signature(x = "NodeList", y = "NodeList"), 78 | definition = function(x, y) { 79 | if (x@node_class == y@node_class) { 80 | x@.Data <- vec_c(x@.Data, y@.Data) 81 | } 82 | return(x) 83 | } 84 | ) 85 | 86 | setMethod( 87 | f = "description", 88 | signature = "NodeList", 89 | definition = function(x) { 90 | TreeDescription(class(x), purrr::map_chr(x, description)) 91 | } 92 | ) 93 | 94 | NamedNodeList <- setClass( 95 | "NamedNodeList", 96 | contains = "NodeList", 97 | prototype = prototype(node_class = "NamedNode") 98 | ) 99 | 100 | setMethod( 101 | f = "initialize", 102 | signature = "NamedNodeList", 103 | definition = function(.Object, ...){ 104 | .Object <- callNextMethod(.Object, ...) 105 | if (length(.Object) > 0) { 106 | nms <- purrr::map_chr(.Object, "name") 107 | names(.Object) <- nms 108 | } 109 | return(.Object) 110 | } 111 | ) 112 | 113 | 114 | 115 | setMethod( 116 | f = "combine", 117 | signature = signature(x = "NamedNodeList", y = "NamedNode"), 118 | definition = function(x, y) { 119 | if (is(y, x@node_class)) { 120 | x[[y@name]] <- y 121 | } 122 | return(x) 123 | } 124 | ) 125 | 126 | setMethod( 127 | f = "combine", 128 | signature = signature(x = "NamedNodeList", y = "NamedNodeList"), 129 | definition = function(x, y) { 130 | if (x@node_class == y@node_class) { 131 | new_names <- vec_c(names(x), names(y)) 132 | x@.Data <- vec_c(x@.Data, y@.Data) 133 | names(x) <- new_names 134 | } 135 | return(x) 136 | } 137 | ) 138 | 139 | 140 | -------------------------------------------------------------------------------- /R/pk_model.R: -------------------------------------------------------------------------------- 1 | #' @include facet.R 2 | #' @include nm_model.R 3 | #' @include model.R 4 | PkModel <- setClass("PkModel", contains = "GenericModel") 5 | 6 | setMethod( 7 | f = "initialize", 8 | signature = "PkModel", 9 | definition = function(.Object, ...) { 10 | callNextMethod(.Object, 11 | facets = list(ParameterFacet(), 12 | AlgebraicFacet(), 13 | PkComponentFacet(), 14 | ObservationFacet(), 15 | InputVariableFacet(), 16 | MetadataFacet()), 17 | ...) 18 | } 19 | ) 20 | 21 | setMethod( 22 | f = "show", 23 | signature = "PkModel", 24 | definition = function(object) { 25 | print_shortened_tree_description( 26 | tree_description = compact_description(object), 27 | type = "pk_model", 28 | child_type = "facet{?s}", 29 | show = c("PkComponentFacet","ParameterFacet", "AlgebraicFacet", "ObservationFacet") 30 | ) 31 | print_issues_warning(check_component(object)) 32 | } 33 | ) 34 | 35 | 36 | #' Create a PK model 37 | #' 38 | #' This function creates the basis for a pharmacokinetic model. 39 | #' 40 | #' The function creates the foundation for a pharmacokinetic model to which different building blocks can be added. 41 | #' The following building blocks are relevant for this model type: 42 | #' 43 | #' * Parameters: `r md_doc_links_for_package_functions("^prm_")` 44 | #' * Observations: `r md_doc_links_for_package_functions("^obs_")` 45 | #' * Algebraic relationships: [algebraic] 46 | #' * PK components: `r md_doc_links_for_package_functions("^pk_")` 47 | #' * Input variables: [input_variable], [dataset] 48 | #' 49 | #' @return A pk_model 50 | #' @md 51 | #' @export 52 | pk_model <- function(){ 53 | PkModel() 54 | } 55 | 56 | 57 | setMethod( 58 | f = "convert", 59 | signature = c(target = "Model", source = "PkModel", component = "missing"), 60 | definition = function(target, source, component, options) { 61 | # ensure to process in alphabetical order (i.e., absorption, distribution, elimination) 62 | cmp_order <- order(names(source@facets[["PkComponentFacet"]]@entries)) 63 | source@facets[["PkComponentFacet"]]@entries <- source@facets[["PkComponentFacet"]]@entries[cmp_order] 64 | target <- convert(target, source, source@facets[["PkComponentFacet"]], options = options) 65 | purrr::discard(source@facets, ~inherits(.x, "PkComponentFacet")) %>% 66 | purrr::reduce(combine, .init = target) 67 | } 68 | ) 69 | 70 | 71 | 72 | -------------------------------------------------------------------------------- /R/statement.R: -------------------------------------------------------------------------------- 1 | #' @include rendering.R 2 | 3 | 4 | new_statement <- function(expr = list()){ 5 | vec_assert(expr, ptype = list()) 6 | if (!rlang::is_empty(expr) && all(!purrr::map_lgl(expr, rlang::is_expression))) 7 | rlang::abort(message = "`expr` must be an expression") 8 | new_vctr(expr, class = "assemblerr_statement") 9 | } 10 | 11 | statement <- function(..., .envir = parent.frame()){ 12 | dots <- rlang::dots_list(..., .named = FALSE) %>% 13 | rlang::set_names(NULL) %>% 14 | purrr::map_if(is.character, ~rlang::parse_expr(glue::glue(.x, .envir = .envir))) 15 | new_statement(expr = dots) 16 | } 17 | 18 | setOldClass("assemblerr_statement") 19 | 20 | #' @export 21 | format.assemblerr_statement <- function(x, ...){ 22 | purrr::map(x, deparse, width.cutoff = 20L) %>% 23 | purrr::map(trimws) %>% 24 | purrr::map_chr(paste, collapse = ";") %>% 25 | purrr::modify_if(~nchar(.x)>20, ~paste0(substr(.x, 1, 20), "...")) 26 | } 27 | 28 | as_statement <- function(x, ...){ 29 | UseMethod("as_statement") 30 | } 31 | 32 | as_statement.assemblerr_declaration <- function(x, ...){ 33 | ids <- dcl_id(x) 34 | defs <- dcl_def(x) 35 | exprs <- purrr::map2( 36 | .x = ids, 37 | .y = defs, 38 | .f = function(id, def) { 39 | if (is.null(id)) { 40 | bquote(.(def)) 41 | }else{ 42 | bquote(.(id) <- .(def)) 43 | } 44 | } 45 | ) 46 | statement(!!!exprs) 47 | } 48 | 49 | vec_ptype_abbr.assemblerr_statement <- function(x, ...) "stm" 50 | vec_ptype_full.assemblerr_statement <- function(x, ...) "statement" 51 | 52 | 53 | setMethod( 54 | f = "render_component", 55 | signature = c(x = "assemblerr_statement"), 56 | definition = function(x) { 57 | vec_data(x) %>% 58 | purrr::map(transform_ast, transformer = vec2fcall_transformer) %>% 59 | purrr::map(transform_ast, transformer = assignment_transformer) %>% 60 | purrr::map_chr(deparse, control = c(), width.cutoff = 200) %>% 61 | glue::glue_collapse(sep = "\n") %>% 62 | toupper() 63 | } 64 | ) 65 | 66 | 67 | assignment_transformer <- function(node){ 68 | if (rlang::is_call(node) && rlang::call_name(node) == "<-") { 69 | node[[1]] <- quote(`=`) 70 | } 71 | node 72 | } 73 | 74 | vec2fcall_transformer <- function(node){ 75 | if (rlang::is_call(node) && rlang::call_name(node) == "[") { 76 | node[[1]] <- node[[2]] 77 | node[[2]] <- NULL 78 | } 79 | node 80 | } 81 | -------------------------------------------------------------------------------- /R/util.R: -------------------------------------------------------------------------------- 1 | sym <- function(...) rlang::sym(do.call(paste0, args = list(...))) 2 | 3 | 4 | name_index_map <- function(x){ 5 | names(x) %>% 6 | {purrr::set_names(seq_along(.),.)} 7 | } 8 | 9 | generate_permutations <- function(indicies){ 10 | if (vec_size(indicies) == 1) return(indicies) 11 | permutations <- matrix(nrow = 0, ncol = length(indicies)) 12 | for (i in seq_along(indicies)) { 13 | permutations <- rbind(permutations, 14 | cbind(indicies[i], generate_permutations(indicies[-i]))) 15 | } 16 | return(permutations) 17 | } 18 | 19 | permutation_matrix <- function(index){ 20 | purrr::map(index, ~as.numeric(seq_along(index)==.x)) %>% 21 | do.call(cbind, args = .) 22 | } 23 | 24 | 25 | is_valid_variable_name <- function(name){ 26 | grepl(x = name, pattern = "^[a-zA-Z][0-9a-zA-Z_]*$") 27 | } 28 | 29 | #' Convert facet class names to labels 30 | #' 31 | #' @param names Character vector of facet class names 32 | #' 33 | #' @return Character vector with class names translated to labels 34 | #' @export 35 | #' @examples 36 | #' assemblerr:::facet_names_to_labels(c("ParameterFacet", "InputVariableFacet")) 37 | #' @keywords internal 38 | facet_names_to_labels <- function(names) { 39 | names[grepl("Facet$", names)] <- names[grepl("Facet$", names)] %>% 40 | gsub("Facet$","", x = .) %>% 41 | split_camelcase() %>% 42 | tolower() 43 | names 44 | } 45 | 46 | split_camelcase <- function(x) gsub("\\B([A-Z])", " \\1", x = x) 47 | 48 | #' Perform string interpolation with pluralization 49 | #' 50 | #' @param ... Character vectors to interpolate 51 | #' @param .envir Environment for lookup 52 | #' 53 | #' @return A character vector 54 | #' @export 55 | #' @examples 56 | #' x <- 1:10 57 | #' assemblerr:::interp("x has elements {x}") 58 | #' @keywords internal 59 | interp <- function(..., .envir = parent.frame()) { 60 | res <- cli::pluralize(..., .envir = .envir) 61 | as.character(res) 62 | } 63 | 64 | #'@importFrom cli qty 65 | 66 | none <- function(x) { 67 | if (vec_is_empty(x)) return(cli::col_grey("none")) 68 | x 69 | } 70 | 71 | sq <- function(x) { 72 | return(paste0("'",x,"'")) 73 | } 74 | 75 | #' Create documentation links functions 76 | #' 77 | #' Creates a string with the Markdown code linking to the doc for all function that match the specifed pattern. 78 | #' 79 | #' @param pattern Regular expression to select the package functions 80 | #' 81 | #' @return Character vector of length 1 82 | #' @export 83 | #' @keywords internal 84 | #' 85 | #' @examples 86 | #' md_doc_links_for_package_functions("^prm_") 87 | #' @importFrom utils lsf.str 88 | md_doc_links_for_package_functions <- function(pattern) { 89 | lsf.str("package:assemblerr", pattern = pattern) %>% 90 | paste0("[", . , "]") %>% 91 | paste(collapse = ", ") 92 | } 93 | 94 | list_fns <- function(pattern) { 95 | lsf.str("package:assemblerr", pattern = pattern) 96 | } 97 | 98 | list_combs <- function(...) { 99 | rlang::list2(...) %>% 100 | purrr::map(list_fns) %>% 101 | purrr::cross_df() 102 | } 103 | 104 | generate_unique_name_mapping <- function(variables) { 105 | mapping <- character() 106 | indicies <- seq_along(variables) 107 | for (i in indicies) { 108 | suffix <- "" 109 | while (any(toupper(variables[indicies < i]) == toupper(paste0(variables[i], suffix)))) { 110 | if (suffix == "") suffix <- 0L 111 | suffix <- suffix + 1L 112 | } 113 | if (is.integer(suffix)) { 114 | mapping[variables[i]] <- paste0(variables[i], suffix) 115 | variables[i] <- paste0(variables[i], suffix) 116 | } 117 | } 118 | return(mapping) 119 | } 120 | 121 | -------------------------------------------------------------------------------- /README.Rmd: -------------------------------------------------------------------------------- 1 | --- 2 | output: github_document 3 | --- 4 | 5 | 6 | 7 | ```{r, include = FALSE} 8 | knitr::opts_chunk$set( 9 | collapse = TRUE, 10 | comment = "#>", 11 | fig.path = "man/figures/README-", 12 | out.width = "100%" 13 | ) 14 | ``` 15 | 16 | # assemblerr 17 | 18 | 19 | 20 | [![R-CMD-check](https://github.com/UUPharmacometrics/assemblerr/workflows/R-CMD-check/badge.svg)](https://github.com/UUPharmacometrics/assemblerr/actions) 21 | [![Codecov test coverage](https://codecov.io/gh/UUPharmacometrics/assemblerr/branch/master/graph/badge.svg)](https://app.codecov.io/gh/UUPharmacometrics/assemblerr?branch=master) 22 | [![CRAN status](https://www.r-pkg.org/badges/version/assemblerr)](https://CRAN.R-project.org/package=assemblerr) 23 | 24 | 25 | 26 | 27 | assemblerr is an R package to construct pharmacometric models by combining pre-defined model components. It's intended to simplify the specification of complex pharmacometric models and provide a mechanism to generate models in an automatic way. With assemblerr, models are specified using R code and then converted to a NONMEM control stream. 28 | 29 | ## Installation 30 | 31 | You can install the latest CRAN version `assemblerr` using: 32 | 33 | ``` r 34 | install.packages("assemblerr") 35 | ``` 36 | 37 | ## Quick start 38 | 39 | **Load assemblerr** 40 | 41 | ```{r} 42 | library(assemblerr) 43 | ``` 44 | 45 | **Build a simple model** 46 | 47 | ```{r} 48 | m <- model() + 49 | input_variable("dose") + 50 | prm_log_normal("emax", median = 10, var_log = 0.09) + 51 | prm_log_normal("ed50", median = 50, var_log = 0.09) + 52 | algebraic(effect~emax*dose/(ed50 + dose)) + 53 | obs_additive(~effect, var_add = 1) 54 | 55 | ``` 56 | 57 | 58 | **Generate NONMEM code** 59 | 60 | ```{r} 61 | render(m) 62 | ``` 63 | 64 | 65 | ## Learning more 66 | 67 | The best place to learn how to use assemblerr is the vignette "Getting Started". It provides an overview of the functionality in assemblerr and helps you building your own models. A simple way to find it is using the `vignette()` function in R: 68 | 69 | ``` r 70 | vignette("getting-started", package = "assemblerr") 71 | ``` 72 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | # assemblerr 5 | 6 | 7 | 8 | [![R-CMD-check](https://github.com/UUPharmacometrics/assemblerr/workflows/R-CMD-check/badge.svg)](https://github.com/UUPharmacometrics/assemblerr/actions) 9 | [![Codecov test 10 | coverage](https://codecov.io/gh/UUPharmacometrics/assemblerr/branch/master/graph/badge.svg)](https://app.codecov.io/gh/UUPharmacometrics/assemblerr?branch=master) 11 | [![CRAN 12 | status](https://www.r-pkg.org/badges/version/assemblerr)](https://CRAN.R-project.org/package=assemblerr) 13 | 14 | 15 | assemblerr is an R package to construct pharmacometric models by 16 | combining pre-defined model components. It’s intended to simplify the 17 | specification of complex pharmacometric models and provide a mechanism 18 | to generate models in an automatic way. With assemblerr, models are 19 | specified using R code and then converted to a NONMEM control stream. 20 | 21 | ## Installation 22 | 23 | You can install the latest CRAN version `assemblerr` using: 24 | 25 | ``` r 26 | install.packages("assemblerr") 27 | ``` 28 | 29 | ## Quick start 30 | 31 | **Load assemblerr** 32 | 33 | ``` r 34 | library(assemblerr) 35 | ``` 36 | 37 | **Build a simple model** 38 | 39 | ``` r 40 | m <- model() + 41 | input_variable("dose") + 42 | prm_log_normal("emax", median = 10, var_log = 0.09) + 43 | prm_log_normal("ed50", median = 50, var_log = 0.09) + 44 | algebraic(effect~emax*dose/(ed50 + dose)) + 45 | obs_additive(~effect, var_add = 1) 46 | ``` 47 | 48 | **Generate NONMEM code** 49 | 50 | ``` r 51 | render(m) 52 | #> $PROBLEM 53 | #> $INPUT DOSE ID DV 54 | #> $DATA data.csv IGNORE=@ 55 | #> $PRED 56 | #> EMAX = THETA(1) * EXP(ETA(1)) 57 | #> ED50 = THETA(2) * EXP(ETA(2)) 58 | #> EFFECT = EMAX * DOSE/(ED50 + DOSE) 59 | #> Y = EFFECT + EPS(1) 60 | #> $ESTIMATION METHOD=COND MAXEVAL=999999 61 | #> $THETA (0, 10, Inf) ; POP_EMAX 62 | #> $THETA (0, 50, Inf) ; POP_ED50 63 | #> $OMEGA 0.09 ; IIV_EMAX 64 | #> $OMEGA 0.09 ; IIV_ED50 65 | #> $SIGMA 1; RUV_ADD 66 | ``` 67 | 68 | ## Learning more 69 | 70 | The best place to learn how to use assemblerr is the vignette “Getting 71 | Started”. It provides an overview of the functionality in assemblerr and 72 | helps you building your own models. A simple way to find it is using the 73 | `vignette()` function in R: 74 | 75 | ``` r 76 | vignette("getting-started", package = "assemblerr") 77 | ``` 78 | -------------------------------------------------------------------------------- /_pkgdown.yml: -------------------------------------------------------------------------------- 1 | url: https://uupharmacometrics.github.io/assemblerr/ 2 | templates: 3 | params: 4 | bootswatch: Flatly 5 | 6 | development: 7 | mode: auto 8 | 9 | reference: 10 | - title: "Model constructors" 11 | desc: > 12 | Functions to create the foundation of a model. 13 | - contents: 14 | - model 15 | - pk_model 16 | 17 | - title: "Parameter models" 18 | desc: "Building blocks defining parameters" 19 | - contents: 20 | - starts_with("prm_") 21 | 22 | - title: "Observation models" 23 | desc: "Building blocks defining observations" 24 | - contents: 25 | - starts_with("obs_") 26 | 27 | - title: "Compartments" 28 | desc: "Building blocks to define compartments and flows" 29 | - contents: 30 | - compartment 31 | - cmp 32 | - flow 33 | 34 | - title: "Algebraics & variables" 35 | desc: "Building blocks to specify algebraic relationships and input variables" 36 | - contents: 37 | - algebraic 38 | - input_variable 39 | 40 | - title: "PK components" 41 | desc: "Building blocks to define pharmacokinetic components" 42 | - contents: 43 | - starts_with("pk_") 44 | 45 | 46 | - title: "Checking & Rendering" 47 | desc: "Check a model and converting it into code" 48 | - contents: 49 | - check 50 | - render 51 | - assemblerr_options 52 | 53 | - title: "Model tasks" 54 | desc: "Specifying model tasks" 55 | - contents: 56 | - starts_with("tsk_") 57 | - model-variable-selection 58 | -------------------------------------------------------------------------------- /assemblerr.Rproj: -------------------------------------------------------------------------------- 1 | Version: 1.0 2 | 3 | RestoreWorkspace: No 4 | SaveWorkspace: No 5 | AlwaysSaveHistory: Default 6 | 7 | EnableCodeIndexing: Yes 8 | UseSpacesForTab: Yes 9 | NumSpacesForTab: 2 10 | Encoding: UTF-8 11 | 12 | RnwWeave: Sweave 13 | LaTeX: pdfLaTeX 14 | 15 | AutoAppendNewline: Yes 16 | StripTrailingWhitespace: Yes 17 | 18 | BuildType: Package 19 | PackageUseDevtools: Yes 20 | PackageInstallArgs: --no-multiarch --with-keep.source 21 | PackageRoxygenize: rd,collate,namespace,vignette 22 | -------------------------------------------------------------------------------- /codecov.yml: -------------------------------------------------------------------------------- 1 | comment: false 2 | 3 | coverage: 4 | status: 5 | project: 6 | default: 7 | target: auto 8 | threshold: 1% 9 | patch: 10 | default: 11 | target: auto 12 | threshold: 1% 13 | -------------------------------------------------------------------------------- /cran-comments.md: -------------------------------------------------------------------------------- 1 | ## Resubmission 2 | 3 | This is a resubmission. In this version I have: 4 | 5 | * fixed the code coverage URL 6 | 7 | ## Patch release 8 | 9 | * fix broken tests after changes in dependencies 10 | 11 | ## Test environments 12 | 13 | * local R installation, R 3.5.2 14 | * Windows - latest, R 4.1.2 15 | * macOS - latest, R 4.1.2 16 | * Ubuntu - 20.04, R 4.1.2 17 | * Ubuntu - 20.04, R devel 18 | 19 | ## R CMD check results 20 | 21 | 0 errors | 0 warnings | 0 note 22 | 23 | 24 | -------------------------------------------------------------------------------- /docs/bootstrap-toc.css: -------------------------------------------------------------------------------- 1 | /*! 2 | * Bootstrap Table of Contents v0.4.1 (http://afeld.github.io/bootstrap-toc/) 3 | * Copyright 2015 Aidan Feldman 4 | * Licensed under MIT (https://github.com/afeld/bootstrap-toc/blob/gh-pages/LICENSE.md) */ 5 | 6 | /* modified from https://github.com/twbs/bootstrap/blob/94b4076dd2efba9af71f0b18d4ee4b163aa9e0dd/docs/assets/css/src/docs.css#L548-L601 */ 7 | 8 | /* All levels of nav */ 9 | nav[data-toggle='toc'] .nav > li > a { 10 | display: block; 11 | padding: 4px 20px; 12 | font-size: 13px; 13 | font-weight: 500; 14 | color: #767676; 15 | } 16 | nav[data-toggle='toc'] .nav > li > a:hover, 17 | nav[data-toggle='toc'] .nav > li > a:focus { 18 | padding-left: 19px; 19 | color: #563d7c; 20 | text-decoration: none; 21 | background-color: transparent; 22 | border-left: 1px solid #563d7c; 23 | } 24 | nav[data-toggle='toc'] .nav > .active > a, 25 | nav[data-toggle='toc'] .nav > .active:hover > a, 26 | nav[data-toggle='toc'] .nav > .active:focus > a { 27 | padding-left: 18px; 28 | font-weight: bold; 29 | color: #563d7c; 30 | background-color: transparent; 31 | border-left: 2px solid #563d7c; 32 | } 33 | 34 | /* Nav: second level (shown on .active) */ 35 | nav[data-toggle='toc'] .nav .nav { 36 | display: none; /* Hide by default, but at >768px, show it */ 37 | padding-bottom: 10px; 38 | } 39 | nav[data-toggle='toc'] .nav .nav > li > a { 40 | padding-top: 1px; 41 | padding-bottom: 1px; 42 | padding-left: 30px; 43 | font-size: 12px; 44 | font-weight: normal; 45 | } 46 | nav[data-toggle='toc'] .nav .nav > li > a:hover, 47 | nav[data-toggle='toc'] .nav .nav > li > a:focus { 48 | padding-left: 29px; 49 | } 50 | nav[data-toggle='toc'] .nav .nav > .active > a, 51 | nav[data-toggle='toc'] .nav .nav > .active:hover > a, 52 | nav[data-toggle='toc'] .nav .nav > .active:focus > a { 53 | padding-left: 28px; 54 | font-weight: 500; 55 | } 56 | 57 | /* from https://github.com/twbs/bootstrap/blob/e38f066d8c203c3e032da0ff23cd2d6098ee2dd6/docs/assets/css/src/docs.css#L631-L634 */ 58 | nav[data-toggle='toc'] .nav > .active > ul { 59 | display: block; 60 | } 61 | -------------------------------------------------------------------------------- /docs/dev/bootstrap-toc.css: -------------------------------------------------------------------------------- 1 | /*! 2 | * Bootstrap Table of Contents v0.4.1 (http://afeld.github.io/bootstrap-toc/) 3 | * Copyright 2015 Aidan Feldman 4 | * Licensed under MIT (https://github.com/afeld/bootstrap-toc/blob/gh-pages/LICENSE.md) */ 5 | 6 | /* modified from https://github.com/twbs/bootstrap/blob/94b4076dd2efba9af71f0b18d4ee4b163aa9e0dd/docs/assets/css/src/docs.css#L548-L601 */ 7 | 8 | /* All levels of nav */ 9 | nav[data-toggle='toc'] .nav > li > a { 10 | display: block; 11 | padding: 4px 20px; 12 | font-size: 13px; 13 | font-weight: 500; 14 | color: #767676; 15 | } 16 | nav[data-toggle='toc'] .nav > li > a:hover, 17 | nav[data-toggle='toc'] .nav > li > a:focus { 18 | padding-left: 19px; 19 | color: #563d7c; 20 | text-decoration: none; 21 | background-color: transparent; 22 | border-left: 1px solid #563d7c; 23 | } 24 | nav[data-toggle='toc'] .nav > .active > a, 25 | nav[data-toggle='toc'] .nav > .active:hover > a, 26 | nav[data-toggle='toc'] .nav > .active:focus > a { 27 | padding-left: 18px; 28 | font-weight: bold; 29 | color: #563d7c; 30 | background-color: transparent; 31 | border-left: 2px solid #563d7c; 32 | } 33 | 34 | /* Nav: second level (shown on .active) */ 35 | nav[data-toggle='toc'] .nav .nav { 36 | display: none; /* Hide by default, but at >768px, show it */ 37 | padding-bottom: 10px; 38 | } 39 | nav[data-toggle='toc'] .nav .nav > li > a { 40 | padding-top: 1px; 41 | padding-bottom: 1px; 42 | padding-left: 30px; 43 | font-size: 12px; 44 | font-weight: normal; 45 | } 46 | nav[data-toggle='toc'] .nav .nav > li > a:hover, 47 | nav[data-toggle='toc'] .nav .nav > li > a:focus { 48 | padding-left: 29px; 49 | } 50 | nav[data-toggle='toc'] .nav .nav > .active > a, 51 | nav[data-toggle='toc'] .nav .nav > .active:hover > a, 52 | nav[data-toggle='toc'] .nav .nav > .active:focus > a { 53 | padding-left: 28px; 54 | font-weight: 500; 55 | } 56 | 57 | /* from https://github.com/twbs/bootstrap/blob/e38f066d8c203c3e032da0ff23cd2d6098ee2dd6/docs/assets/css/src/docs.css#L631-L634 */ 58 | nav[data-toggle='toc'] .nav > .active > ul { 59 | display: block; 60 | } 61 | -------------------------------------------------------------------------------- /docs/dev/docsearch.js: -------------------------------------------------------------------------------- 1 | $(function() { 2 | 3 | // register a handler to move the focus to the search bar 4 | // upon pressing shift + "/" (i.e. "?") 5 | $(document).on('keydown', function(e) { 6 | if (e.shiftKey && e.keyCode == 191) { 7 | e.preventDefault(); 8 | $("#search-input").focus(); 9 | } 10 | }); 11 | 12 | $(document).ready(function() { 13 | // do keyword highlighting 14 | /* modified from https://jsfiddle.net/julmot/bL6bb5oo/ */ 15 | var mark = function() { 16 | 17 | var referrer = document.URL ; 18 | var paramKey = "q" ; 19 | 20 | if (referrer.indexOf("?") !== -1) { 21 | var qs = referrer.substr(referrer.indexOf('?') + 1); 22 | var qs_noanchor = qs.split('#')[0]; 23 | var qsa = qs_noanchor.split('&'); 24 | var keyword = ""; 25 | 26 | for (var i = 0; i < qsa.length; i++) { 27 | var currentParam = qsa[i].split('='); 28 | 29 | if (currentParam.length !== 2) { 30 | continue; 31 | } 32 | 33 | if (currentParam[0] == paramKey) { 34 | keyword = decodeURIComponent(currentParam[1].replace(/\+/g, "%20")); 35 | } 36 | } 37 | 38 | if (keyword !== "") { 39 | $(".contents").unmark({ 40 | done: function() { 41 | $(".contents").mark(keyword); 42 | } 43 | }); 44 | } 45 | } 46 | }; 47 | 48 | mark(); 49 | }); 50 | }); 51 | 52 | /* Search term highlighting ------------------------------*/ 53 | 54 | function matchedWords(hit) { 55 | var words = []; 56 | 57 | var hierarchy = hit._highlightResult.hierarchy; 58 | // loop to fetch from lvl0, lvl1, etc. 59 | for (var idx in hierarchy) { 60 | words = words.concat(hierarchy[idx].matchedWords); 61 | } 62 | 63 | var content = hit._highlightResult.content; 64 | if (content) { 65 | words = words.concat(content.matchedWords); 66 | } 67 | 68 | // return unique words 69 | var words_uniq = [...new Set(words)]; 70 | return words_uniq; 71 | } 72 | 73 | function updateHitURL(hit) { 74 | 75 | var words = matchedWords(hit); 76 | var url = ""; 77 | 78 | if (hit.anchor) { 79 | url = hit.url_without_anchor + '?q=' + escape(words.join(" ")) + '#' + hit.anchor; 80 | } else { 81 | url = hit.url + '?q=' + escape(words.join(" ")); 82 | } 83 | 84 | return url; 85 | } 86 | -------------------------------------------------------------------------------- /docs/dev/link.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | 8 | 12 | 13 | -------------------------------------------------------------------------------- /docs/dev/pkgdown.js: -------------------------------------------------------------------------------- 1 | /* http://gregfranko.com/blog/jquery-best-practices/ */ 2 | (function($) { 3 | $(function() { 4 | 5 | $('.navbar-fixed-top').headroom(); 6 | 7 | $('body').css('padding-top', $('.navbar').height() + 10); 8 | $(window).resize(function(){ 9 | $('body').css('padding-top', $('.navbar').height() + 10); 10 | }); 11 | 12 | $('[data-toggle="tooltip"]').tooltip(); 13 | 14 | var cur_path = paths(location.pathname); 15 | var links = $("#navbar ul li a"); 16 | var max_length = -1; 17 | var pos = -1; 18 | for (var i = 0; i < links.length; i++) { 19 | if (links[i].getAttribute("href") === "#") 20 | continue; 21 | // Ignore external links 22 | if (links[i].host !== location.host) 23 | continue; 24 | 25 | var nav_path = paths(links[i].pathname); 26 | 27 | var length = prefix_length(nav_path, cur_path); 28 | if (length > max_length) { 29 | max_length = length; 30 | pos = i; 31 | } 32 | } 33 | 34 | // Add class to parent
  • , and enclosing
  • if in dropdown 35 | if (pos >= 0) { 36 | var menu_anchor = $(links[pos]); 37 | menu_anchor.parent().addClass("active"); 38 | menu_anchor.closest("li.dropdown").addClass("active"); 39 | } 40 | }); 41 | 42 | function paths(pathname) { 43 | var pieces = pathname.split("/"); 44 | pieces.shift(); // always starts with / 45 | 46 | var end = pieces[pieces.length - 1]; 47 | if (end === "index.html" || end === "") 48 | pieces.pop(); 49 | return(pieces); 50 | } 51 | 52 | // Returns -1 if not found 53 | function prefix_length(needle, haystack) { 54 | if (needle.length > haystack.length) 55 | return(-1); 56 | 57 | // Special case for length-0 haystack, since for loop won't run 58 | if (haystack.length === 0) { 59 | return(needle.length === 0 ? 0 : -1); 60 | } 61 | 62 | for (var i = 0; i < haystack.length; i++) { 63 | if (needle[i] != haystack[i]) 64 | return(i); 65 | } 66 | 67 | return(haystack.length); 68 | } 69 | 70 | /* Clipboard --------------------------*/ 71 | 72 | function changeTooltipMessage(element, msg) { 73 | var tooltipOriginalTitle=element.getAttribute('data-original-title'); 74 | element.setAttribute('data-original-title', msg); 75 | $(element).tooltip('show'); 76 | element.setAttribute('data-original-title', tooltipOriginalTitle); 77 | } 78 | 79 | if(ClipboardJS.isSupported()) { 80 | $(document).ready(function() { 81 | var copyButton = ""; 82 | 83 | $("div.sourceCode").addClass("hasCopyButton"); 84 | 85 | // Insert copy buttons: 86 | $(copyButton).prependTo(".hasCopyButton"); 87 | 88 | // Initialize tooltips: 89 | $('.btn-copy-ex').tooltip({container: 'body'}); 90 | 91 | // Initialize clipboard: 92 | var clipboardBtnCopies = new ClipboardJS('[data-clipboard-copy]', { 93 | text: function(trigger) { 94 | return trigger.parentNode.textContent.replace(/\n#>[^\n]*/g, ""); 95 | } 96 | }); 97 | 98 | clipboardBtnCopies.on('success', function(e) { 99 | changeTooltipMessage(e.trigger, 'Copied!'); 100 | e.clearSelection(); 101 | }); 102 | 103 | clipboardBtnCopies.on('error', function() { 104 | changeTooltipMessage(e.trigger,'Press Ctrl+C or Command+C to copy'); 105 | }); 106 | }); 107 | } 108 | })(window.jQuery || window.$) 109 | -------------------------------------------------------------------------------- /docs/dev/pkgdown.yml: -------------------------------------------------------------------------------- 1 | pandoc: '2.5' 2 | pkgdown: 2.0.6 3 | pkgdown_sha: ~ 4 | articles: 5 | getting-started: getting-started.html 6 | last_built: 2022-09-22T15:14Z 7 | urls: 8 | reference: https://uupharmacometrics.github.io/assemblerr/reference 9 | article: https://uupharmacometrics.github.io/assemblerr/articles 10 | 11 | -------------------------------------------------------------------------------- /docs/dev/reference/Rplot001.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UUPharmacometrics/assemblerr/00f8b410470d12bca39445f7186449c820e18177/docs/dev/reference/Rplot001.png -------------------------------------------------------------------------------- /docs/dev/reference/figures/README-pressure-1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UUPharmacometrics/assemblerr/00f8b410470d12bca39445f7186449c820e18177/docs/dev/reference/figures/README-pressure-1.png -------------------------------------------------------------------------------- /docs/docsearch.js: -------------------------------------------------------------------------------- 1 | $(function() { 2 | 3 | // register a handler to move the focus to the search bar 4 | // upon pressing shift + "/" (i.e. "?") 5 | $(document).on('keydown', function(e) { 6 | if (e.shiftKey && e.keyCode == 191) { 7 | e.preventDefault(); 8 | $("#search-input").focus(); 9 | } 10 | }); 11 | 12 | $(document).ready(function() { 13 | // do keyword highlighting 14 | /* modified from https://jsfiddle.net/julmot/bL6bb5oo/ */ 15 | var mark = function() { 16 | 17 | var referrer = document.URL ; 18 | var paramKey = "q" ; 19 | 20 | if (referrer.indexOf("?") !== -1) { 21 | var qs = referrer.substr(referrer.indexOf('?') + 1); 22 | var qs_noanchor = qs.split('#')[0]; 23 | var qsa = qs_noanchor.split('&'); 24 | var keyword = ""; 25 | 26 | for (var i = 0; i < qsa.length; i++) { 27 | var currentParam = qsa[i].split('='); 28 | 29 | if (currentParam.length !== 2) { 30 | continue; 31 | } 32 | 33 | if (currentParam[0] == paramKey) { 34 | keyword = decodeURIComponent(currentParam[1].replace(/\+/g, "%20")); 35 | } 36 | } 37 | 38 | if (keyword !== "") { 39 | $(".contents").unmark({ 40 | done: function() { 41 | $(".contents").mark(keyword); 42 | } 43 | }); 44 | } 45 | } 46 | }; 47 | 48 | mark(); 49 | }); 50 | }); 51 | 52 | /* Search term highlighting ------------------------------*/ 53 | 54 | function matchedWords(hit) { 55 | var words = []; 56 | 57 | var hierarchy = hit._highlightResult.hierarchy; 58 | // loop to fetch from lvl0, lvl1, etc. 59 | for (var idx in hierarchy) { 60 | words = words.concat(hierarchy[idx].matchedWords); 61 | } 62 | 63 | var content = hit._highlightResult.content; 64 | if (content) { 65 | words = words.concat(content.matchedWords); 66 | } 67 | 68 | // return unique words 69 | var words_uniq = [...new Set(words)]; 70 | return words_uniq; 71 | } 72 | 73 | function updateHitURL(hit) { 74 | 75 | var words = matchedWords(hit); 76 | var url = ""; 77 | 78 | if (hit.anchor) { 79 | url = hit.url_without_anchor + '?q=' + escape(words.join(" ")) + '#' + hit.anchor; 80 | } else { 81 | url = hit.url + '?q=' + escape(words.join(" ")); 82 | } 83 | 84 | return url; 85 | } 86 | -------------------------------------------------------------------------------- /docs/link.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | 8 | 12 | 13 | -------------------------------------------------------------------------------- /docs/pkgdown.js: -------------------------------------------------------------------------------- 1 | /* http://gregfranko.com/blog/jquery-best-practices/ */ 2 | (function($) { 3 | $(function() { 4 | 5 | $('.navbar-fixed-top').headroom(); 6 | 7 | $('body').css('padding-top', $('.navbar').height() + 10); 8 | $(window).resize(function(){ 9 | $('body').css('padding-top', $('.navbar').height() + 10); 10 | }); 11 | 12 | $('[data-toggle="tooltip"]').tooltip(); 13 | 14 | var cur_path = paths(location.pathname); 15 | var links = $("#navbar ul li a"); 16 | var max_length = -1; 17 | var pos = -1; 18 | for (var i = 0; i < links.length; i++) { 19 | if (links[i].getAttribute("href") === "#") 20 | continue; 21 | // Ignore external links 22 | if (links[i].host !== location.host) 23 | continue; 24 | 25 | var nav_path = paths(links[i].pathname); 26 | 27 | var length = prefix_length(nav_path, cur_path); 28 | if (length > max_length) { 29 | max_length = length; 30 | pos = i; 31 | } 32 | } 33 | 34 | // Add class to parent
  • , and enclosing
  • if in dropdown 35 | if (pos >= 0) { 36 | var menu_anchor = $(links[pos]); 37 | menu_anchor.parent().addClass("active"); 38 | menu_anchor.closest("li.dropdown").addClass("active"); 39 | } 40 | }); 41 | 42 | function paths(pathname) { 43 | var pieces = pathname.split("/"); 44 | pieces.shift(); // always starts with / 45 | 46 | var end = pieces[pieces.length - 1]; 47 | if (end === "index.html" || end === "") 48 | pieces.pop(); 49 | return(pieces); 50 | } 51 | 52 | // Returns -1 if not found 53 | function prefix_length(needle, haystack) { 54 | if (needle.length > haystack.length) 55 | return(-1); 56 | 57 | // Special case for length-0 haystack, since for loop won't run 58 | if (haystack.length === 0) { 59 | return(needle.length === 0 ? 0 : -1); 60 | } 61 | 62 | for (var i = 0; i < haystack.length; i++) { 63 | if (needle[i] != haystack[i]) 64 | return(i); 65 | } 66 | 67 | return(haystack.length); 68 | } 69 | 70 | /* Clipboard --------------------------*/ 71 | 72 | function changeTooltipMessage(element, msg) { 73 | var tooltipOriginalTitle=element.getAttribute('data-original-title'); 74 | element.setAttribute('data-original-title', msg); 75 | $(element).tooltip('show'); 76 | element.setAttribute('data-original-title', tooltipOriginalTitle); 77 | } 78 | 79 | if(ClipboardJS.isSupported()) { 80 | $(document).ready(function() { 81 | var copyButton = ""; 82 | 83 | $(".examples, div.sourceCode").addClass("hasCopyButton"); 84 | 85 | // Insert copy buttons: 86 | $(copyButton).prependTo(".hasCopyButton"); 87 | 88 | // Initialize tooltips: 89 | $('.btn-copy-ex').tooltip({container: 'body'}); 90 | 91 | // Initialize clipboard: 92 | var clipboardBtnCopies = new ClipboardJS('[data-clipboard-copy]', { 93 | text: function(trigger) { 94 | return trigger.parentNode.textContent; 95 | } 96 | }); 97 | 98 | clipboardBtnCopies.on('success', function(e) { 99 | changeTooltipMessage(e.trigger, 'Copied!'); 100 | e.clearSelection(); 101 | }); 102 | 103 | clipboardBtnCopies.on('error', function() { 104 | changeTooltipMessage(e.trigger,'Press Ctrl+C or Command+C to copy'); 105 | }); 106 | }); 107 | } 108 | })(window.jQuery || window.$) 109 | -------------------------------------------------------------------------------- /docs/pkgdown.yml: -------------------------------------------------------------------------------- 1 | pandoc: '2.5' 2 | pkgdown: 1.6.1 3 | pkgdown_sha: ~ 4 | articles: 5 | getting-started: getting-started.html 6 | last_built: 2022-01-02T21:50Z 7 | urls: 8 | reference: https://uupharmacometrics.github.io/assemblerr//reference 9 | article: https://uupharmacometrics.github.io/assemblerr//articles 10 | 11 | -------------------------------------------------------------------------------- /docs/reference/Rplot001.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UUPharmacometrics/assemblerr/00f8b410470d12bca39445f7186449c820e18177/docs/reference/Rplot001.png -------------------------------------------------------------------------------- /docs/reference/figures/README-pressure-1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UUPharmacometrics/assemblerr/00f8b410470d12bca39445f7186449c820e18177/docs/reference/figures/README-pressure-1.png -------------------------------------------------------------------------------- /man/algebraic.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/algebraics.R 3 | \name{algebraic} 4 | \alias{algebraic} 5 | \title{Algebraic relationship} 6 | \usage{ 7 | algebraic(definition) 8 | } 9 | \arguments{ 10 | \item{definition}{A definition of the model variable} 11 | } 12 | \value{ 13 | A building block of type 'algebraic' 14 | } 15 | \description{ 16 | This building block defines a model variable as a function of other variables. 17 | } 18 | \details{ 19 | Algebraic relationships are equations where one variable is defined as a function of multiple other variables. assemblerr 20 | uses R formulas to implement these equations. For example, the Emax dose response model 21 | \deqn{effect=emax*dose/(ed50 + dose)} 22 | could be declared as 23 | 24 | \if{html}{\out{
    }}\preformatted{ algebraic(effect~emax*dose/(ed50+dose)) 25 | }\if{html}{\out{
    }} 26 | 27 | where the tilde \code{~} replaced the equal sign \code{=} in the definition. 28 | } 29 | \examples{ 30 | m <- model() + 31 | input_variable("dose") + 32 | prm_log_normal("emax", 10, 0.3) + 33 | prm_no_var("ed50", 5) + 34 | algebraic(effect~emax*dose/(ed50+dose)) + 35 | obs_additive(~effect) 36 | } 37 | -------------------------------------------------------------------------------- /man/assemblerr-package.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/assemblerr-package.R 3 | \docType{package} 4 | \name{assemblerr-package} 5 | \alias{assemblerr} 6 | \alias{assemblerr-package} 7 | \title{assemblerr: Assembly of Pharmacometric Models} 8 | \description{ 9 | Construct pharmacometric nonlinear mixed effect models by combining predefined model components and automatically generate model code for NONMEM. Models are created by combining parameter and observation models, algebraic relationships, compartments, and flows. Pharmacokinetic models can be assembled from the higher-order components: absorption, distribution, and elimination. The generated code is optimized for performance by recognizing, for example, linear differential equations or differential equations with an analytic solution. 10 | } 11 | \seealso{ 12 | Useful links: 13 | \itemize{ 14 | \item \url{https://github.com/UUPharmacometrics/assemblerr} 15 | \item Report bugs at \url{https://github.com/UUPharmacometrics/assemblerr/issues} 16 | } 17 | 18 | } 19 | \author{ 20 | \strong{Maintainer}: Sebastian Ueckert \email{sebastian.ueckert@gmail.com} (\href{https://orcid.org/0000-0002-3712-0255}{ORCID}) [copyright holder] 21 | 22 | Other contributors: 23 | \itemize{ 24 | \item Mats O. Karlsson [scientific advisor] 25 | \item Andrew C. Hooker [scientific advisor] 26 | \item Rikard Nordgren [scientific advisor] 27 | \item Simon Carter [reviewer] 28 | \item Simon Buatois [reviewer] 29 | \item João A. Abrantes [reviewer] 30 | \item F. Hoffmann-La Roche Ltd. [funder] 31 | } 32 | 33 | } 34 | \keyword{internal} 35 | -------------------------------------------------------------------------------- /man/assemblerr-vctrs.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/assemblerr-package.R 3 | \name{assemblerr-vctrs} 4 | \alias{assemblerr-vctrs} 5 | \title{Internal vctrs methods} 6 | \description{ 7 | Internal vctrs methods 8 | } 9 | \keyword{internal} 10 | -------------------------------------------------------------------------------- /man/assemblerr_options.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/model-options.R 3 | \name{assemblerr_options} 4 | \alias{assemblerr_options} 5 | \title{Options} 6 | \usage{ 7 | assemblerr_options( 8 | prm.use_mu_referencing = FALSE, 9 | ode.use_special_advans = TRUE, 10 | ode.use_general_linear_advans = TRUE, 11 | ode.general_nonlinear_advan = "advan13", 12 | ode.general_linear_advan = "advan5", 13 | ode.preferred_trans_routines = c("trans2", "trans4"), 14 | issues.missing_variables = c("fix-warn", "fix", "ignore", "fail") 15 | ) 16 | } 17 | \arguments{ 18 | \item{prm.use_mu_referencing}{Use mu-referencing?} 19 | 20 | \item{ode.use_special_advans}{Use analytic solution ADVANs?} 21 | 22 | \item{ode.use_general_linear_advans}{Use ADVANs for linear ODEs?} 23 | 24 | \item{ode.general_nonlinear_advan}{ADVAN to be used for non-linear ODEs} 25 | 26 | \item{ode.general_linear_advan}{ADVAN to be used for linear ODEs} 27 | 28 | \item{ode.preferred_trans_routines}{Order of TRANS routines to be tried} 29 | 30 | \item{issues.missing_variables}{How to handle missing variables} 31 | } 32 | \value{ 33 | A list of options 34 | } 35 | \description{ 36 | This function creates a list of options for the use with the render function. 37 | } 38 | \details{ 39 | The function helps to create properly formatted list that can serve as input to the \verb{options=} argument 40 | of the \code{render()} function. 41 | } 42 | -------------------------------------------------------------------------------- /man/c-IssueList-method.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/issues.R 3 | \name{c,IssueList-method} 4 | \alias{c,IssueList-method} 5 | \title{Combine issues} 6 | \usage{ 7 | \S4method{c}{IssueList}(x, ...) 8 | } 9 | \arguments{ 10 | \item{x}{An IssueList} 11 | 12 | \item{...}{objects to add to the issue list} 13 | } 14 | \description{ 15 | Combine issues 16 | } 17 | \keyword{internal} 18 | -------------------------------------------------------------------------------- /man/check.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/issues.R 3 | \name{check} 4 | \alias{check} 5 | \title{Checking for issues} 6 | \usage{ 7 | check(model) 8 | } 9 | \arguments{ 10 | \item{model}{Model to check} 11 | } 12 | \value{ 13 | An issue list (printed to the console by default) 14 | } 15 | \description{ 16 | This function checks a model for existing issues. 17 | } 18 | \details{ 19 | The function accepts a model object and returns a list of issues that can help to identify problems in a model. 20 | If no issues are found, a message and an empty list are produced. Issues can either be critical or non-critical, 21 | depending on whether a valid model could still be rendered. 22 | 23 | The function currently detects the following issues: 24 | \itemize{ 25 | \item Undefined variables 26 | \item Lack of parameters 27 | \item Lack of observations 28 | \item Lack of distribution/elimination components (pk_model) 29 | \item Inconsistent capitalization of variable names 30 | } 31 | } 32 | \examples{ 33 | m <- model() + 34 | prm_log_normal("emax") + 35 | prm_log_normal("ed50") + 36 | obs_additive(eff~emax*dose/(ed50+dose)) 37 | check(m) 38 | 39 | # fix issue 40 | m <- m + input_variable("dose") 41 | check(m) 42 | } 43 | -------------------------------------------------------------------------------- /man/compartment.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/compartment.R 3 | \name{compartment} 4 | \alias{compartment} 5 | \alias{cmp} 6 | \title{Compartment} 7 | \usage{ 8 | compartment(name, volume = 1) 9 | 10 | cmp(name, volume = 1) 11 | } 12 | \arguments{ 13 | \item{name}{Name of the compartment} 14 | 15 | \item{volume}{Volume as a number, formula or parameter name} 16 | } 17 | \value{ 18 | A building block of type 'compartment' 19 | } 20 | \description{ 21 | Defines name and volume of a compartment. 22 | } 23 | \details{ 24 | In most applications, compartments contain kinetically homogeneous amount of drug (applications where the compartment 25 | content represents other quantities are also possible). In assemblerr, a compartment is defined by providing a 26 | a name and the compartment volume. 27 | \subsection{Compartment names}{ 28 | 29 | Every compartment must have a valid name. A compartment name can contain letters, numbers as well as the underscore character, and 30 | needs to start with a letter. Adding a compartment with an already existing name will replace the definition of the compartment. 31 | } 32 | 33 | \subsection{Compartment volumes}{ 34 | 35 | The compartment volume can be provided as a number, R formula, or a parameter name. It will be used by assemblerr to replace 36 | references to the compartment concentration (e.g., \code{~C["central"]}) with the corresponding amount divided by volume (e.g., \verb{~A["central]/vc}). 37 | } 38 | } 39 | \examples{ 40 | # model with depot and central compartment 41 | m <- model() + 42 | compartment("depot", volume = 1) + 43 | compartment("central", volume = "vc") + 44 | flow(~ka*A, from = "depot", to = "central") + 45 | flow(~cl*C, from = "central") + 46 | prm_log_normal("ka") + 47 | prm_log_normal("cl") + 48 | prm_log_normal("vc") + 49 | obs_additive(conc~C["central"]) 50 | 51 | render( 52 | model = m, 53 | options = assemblerr_options( 54 | ode.use_special_advans = FALSE, 55 | ode.use_general_linear_advans = FALSE 56 | ) 57 | ) 58 | } 59 | \seealso{ 60 | \link{flow} for how to describe compartment kinetics 61 | } 62 | -------------------------------------------------------------------------------- /man/dcl_add.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/declaration.R 3 | \name{dcl_add} 4 | \alias{dcl_add} 5 | \alias{dcl_substract} 6 | \alias{dcl_multiply} 7 | \alias{dcl_devide} 8 | \title{Arithmetically combine declarations} 9 | \usage{ 10 | dcl_add(dcl1, dcl2, lhs = dcl_id(dcl1)) 11 | 12 | dcl_substract(dcl1, dcl2, lhs = dcl_id(dcl1)) 13 | 14 | dcl_multiply(dcl1, dcl2, lhs = dcl_id(dcl1)) 15 | 16 | dcl_devide(dcl1, dcl2, lhs = dcl_id(dcl1)) 17 | } 18 | \arguments{ 19 | \item{dcl1}{A declaration} 20 | 21 | \item{dcl2}{A declaration} 22 | 23 | \item{lhs}{List of expressions for the left-hand side of the resulting declaration} 24 | } 25 | \value{ 26 | A declaration 27 | } 28 | \description{ 29 | These functions allow to combine two declarations using addition, substraction, multiplication, or division. 30 | } 31 | \section{Functions}{ 32 | \itemize{ 33 | \item \code{dcl_add()}: Addition of the declarations 34 | 35 | \item \code{dcl_substract()}: Substraction of the declarations 36 | 37 | \item \code{dcl_multiply()}: Multiplications of the declarations 38 | 39 | \item \code{dcl_devide()}: Division of the declarations 40 | 41 | }} 42 | \keyword{internal} 43 | -------------------------------------------------------------------------------- /man/dcl_id-set.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/declaration.R 3 | \name{dcl_id<-} 4 | \alias{dcl_id<-} 5 | \title{Set declaration fields} 6 | \usage{ 7 | dcl_id(dcl) <- value 8 | } 9 | \arguments{ 10 | \item{dcl}{A declaration} 11 | 12 | \item{value}{An expression or a list of expressions} 13 | } 14 | \value{ 15 | The modified declaration 16 | } 17 | \description{ 18 | Set declaration fields 19 | } 20 | \keyword{internal} 21 | -------------------------------------------------------------------------------- /man/dcl_id.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/declaration.R 3 | \name{dcl_id} 4 | \alias{dcl_id} 5 | \alias{dcl_def} 6 | \title{Get declaration fields 7 | 8 | These function get identifier or definition fields of a declaration.} 9 | \usage{ 10 | dcl_id(dcl) 11 | 12 | dcl_def(dcl) 13 | } 14 | \arguments{ 15 | \item{dcl}{A declaration} 16 | } 17 | \value{ 18 | An expression 19 | } 20 | \description{ 21 | Get declaration fields 22 | 23 | These function get identifier or definition fields of a declaration. 24 | } 25 | \keyword{internal} 26 | -------------------------------------------------------------------------------- /man/declaration.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/declaration-creation.R 3 | \name{declaration} 4 | \alias{declaration} 5 | \title{Declaration} 6 | \usage{ 7 | declaration(...) 8 | } 9 | \arguments{ 10 | \item{...}{List of R formulae with a single symbol on the left-hand side and a valid R expression on the right} 11 | } 12 | \value{ 13 | A declaration vector 14 | } 15 | \description{ 16 | A declaration is the mathematical definition of a set of variables. It is the lowest level building block for a model 17 | in `assemblerr`. A declaration consists of the variable names being declared (the identifiers) and their definition. The 18 | `declaration` function allows the specification of a declaration using `R` formulae. 19 | } 20 | \examples{ 21 | d <- declaration(cl~theta[1]+eta[1]) 22 | d2 <- declaration(v=theta[2]*exp(eta[2])) 23 | } 24 | \keyword{internal} 25 | -------------------------------------------------------------------------------- /man/facet_names_to_labels.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/util.R 3 | \name{facet_names_to_labels} 4 | \alias{facet_names_to_labels} 5 | \title{Convert facet class names to labels} 6 | \usage{ 7 | facet_names_to_labels(names) 8 | } 9 | \arguments{ 10 | \item{names}{Character vector of facet class names} 11 | } 12 | \value{ 13 | Character vector with class names translated to labels 14 | } 15 | \description{ 16 | Convert facet class names to labels 17 | } 18 | \examples{ 19 | assemblerr:::facet_names_to_labels(c("ParameterFacet", "InputVariableFacet")) 20 | } 21 | \keyword{internal} 22 | -------------------------------------------------------------------------------- /man/figures/README-pressure-1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/UUPharmacometrics/assemblerr/00f8b410470d12bca39445f7186449c820e18177/man/figures/README-pressure-1.png -------------------------------------------------------------------------------- /man/flow.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/compartment.R 3 | \name{flow} 4 | \alias{flow} 5 | \title{Flow between compartments} 6 | \usage{ 7 | flow(definition, from = NA_character_, to = NA_character_) 8 | } 9 | \arguments{ 10 | \item{definition}{Equation describing the flow} 11 | 12 | \item{from}{Name of the source compartment (NA for an inflow without source)} 13 | 14 | \item{to}{Name of the sink compartment (NA for an outflow without sink)} 15 | } 16 | \value{ 17 | A building block of type 'flow' 18 | } 19 | \description{ 20 | This building block describes a flow between compartments. 21 | } 22 | \details{ 23 | Flows define the connections between compartments and the equations according to which exchanges occur. 24 | \subsection{Flow equations}{ 25 | 26 | The first function argument is the flow equation. It is defined using R formulas that can start with the tilde \code{~} operator and do not 27 | need to have a left-hand side (i.e., \code{~k0} is a valid flow definition). 28 | 29 | Flow equations can contains the special variables \code{A} and \code{C} which can be used to refer to the amount and concentration in the compartment specified via 30 | the \verb{from=} argument. For example, the following code creates a flow building block describing the first-order transfer from the depot to the central 31 | compartment 32 | 33 | \if{html}{\out{
    }}\preformatted{flow(~ka*A, "depot", "central") 34 | }\if{html}{\out{
    }} 35 | 36 | When the model is rendered, \code{A} and \code{C} will get replaced with the corresponding compartment reference. assemblerr will raise an error if \code{A} or \code{C} are used 37 | without specifying the \verb{from=} compartment (such as in an inflow). 38 | } 39 | 40 | \subsection{Compartment connections}{ 41 | 42 | The connection between compartments can be specified using the \verb{from=} and \verb{to=} arguments of the function. Setting either \verb{from=} or \verb{to=} to \code{NA} allows 43 | the definition of in and outflows without a source or sink. Setting both arguments to \code{NA} results in error. 44 | } 45 | 46 | \subsection{Conversion to differential equations}{ 47 | 48 | When flows are rendered they are converted to ordinary differential equations (ODEs). The connection between compartments together with the flow equations allow 49 | assemblerr to determine whether an analytic solution can be generated. This automatic optimization of differential equations can be disabled via the rendering 50 | options. 51 | } 52 | } 53 | \examples{ 54 | # one-compartment model with first-order elimination 55 | m <- model() + 56 | prm_log_normal("v") + 57 | prm_log_normal("cl") + 58 | compartment("central", volume = ~v) + 59 | flow(declaration(~cl*C), from = "central") + 60 | obs_additive(~C["central"]) 61 | # an analytic solution is generated 62 | render(m) 63 | 64 | # one-compartment model with Michaelis-Menten elimination 65 | m2 <- model() + 66 | prm_log_normal("v") + 67 | prm_log_normal("vmax") + 68 | prm_no_var("km") + 69 | compartment("central", volume = ~v) + 70 | flow(declaration(~vmax*C/(km+C)), from = "central") + 71 | obs_additive(~C["central"]) 72 | 73 | # an ODE is generated 74 | render(m2) 75 | } 76 | -------------------------------------------------------------------------------- /man/input_variables.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/input_variable.R 3 | \name{input_variable} 4 | \alias{input_variable} 5 | \alias{dataset} 6 | \title{Input variables} 7 | \usage{ 8 | input_variable(name) 9 | 10 | dataset(path, use_only_filename = FALSE) 11 | } 12 | \arguments{ 13 | \item{name}{Variable name} 14 | 15 | \item{path}{Dataset path} 16 | 17 | \item{use_only_filename}{Whether to include the path of the file} 18 | } 19 | \value{ 20 | A building block of type 'input_variable' 21 | } 22 | \description{ 23 | These building block declare input variables, i.e., variables that are defined in the dataset. 24 | } 25 | \details{ 26 | An input variable is defined in the dataset and is declared so that it can be used in the rest of the model definition. The function 27 | \code{input_variable()} declares a single variable whereas the \code{dataset()} function reads the header of the file provided and 28 | declares all variables found. 29 | } 30 | \examples{ 31 | m <- model() + 32 | input_variable("dose") + 33 | prm_log_normal("emax") + 34 | prm_log_normal("ed50") + 35 | obs_additive(eff~emax*dose/(ed50+dose)) 36 | render(m) 37 | } 38 | -------------------------------------------------------------------------------- /man/interp.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/util.R 3 | \name{interp} 4 | \alias{interp} 5 | \title{Perform string interpolation with pluralization} 6 | \usage{ 7 | interp(..., .envir = parent.frame()) 8 | } 9 | \arguments{ 10 | \item{...}{Character vectors to interpolate} 11 | 12 | \item{.envir}{Environment for lookup} 13 | } 14 | \value{ 15 | A character vector 16 | } 17 | \description{ 18 | Perform string interpolation with pluralization 19 | } 20 | \examples{ 21 | x <- 1:10 22 | assemblerr:::interp("x has elements {x}") 23 | } 24 | \keyword{internal} 25 | -------------------------------------------------------------------------------- /man/is_valid_lhs.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/declaration.R 3 | \name{is_valid_lhs} 4 | \alias{is_valid_lhs} 5 | \title{Test if an expression is a valid LHS for a declaration} 6 | \usage{ 7 | is_valid_lhs(expr) 8 | } 9 | \arguments{ 10 | \item{expr}{an expression} 11 | } 12 | \value{ 13 | TRUE/FALSE 14 | } 15 | \description{ 16 | Test if an expression is a valid LHS for a declaration 17 | } 18 | \keyword{internal} 19 | -------------------------------------------------------------------------------- /man/md_doc_links_for_package_functions.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/util.R 3 | \name{md_doc_links_for_package_functions} 4 | \alias{md_doc_links_for_package_functions} 5 | \title{Create documentation links functions} 6 | \usage{ 7 | md_doc_links_for_package_functions(pattern) 8 | } 9 | \arguments{ 10 | \item{pattern}{Regular expression to select the package functions} 11 | } 12 | \value{ 13 | Character vector of length 1 14 | } 15 | \description{ 16 | Creates a string with the Markdown code linking to the doc for all function that match the specifed pattern. 17 | } 18 | \examples{ 19 | md_doc_links_for_package_functions("^prm_") 20 | } 21 | \keyword{internal} 22 | -------------------------------------------------------------------------------- /man/model-variable-selection.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/variables.R 3 | \name{model-variable-selection} 4 | \alias{model-variable-selection} 5 | \alias{vars_prms} 6 | \alias{vars_data} 7 | \alias{vars_eta} 8 | \alias{vars_nm_std} 9 | \alias{vars_starts_with} 10 | \alias{vars_matches} 11 | \title{Selecting model variables} 12 | \usage{ 13 | vars_prms(vars) 14 | 15 | vars_data(vars) 16 | 17 | vars_eta(vars) 18 | 19 | vars_nm_std(vars) 20 | 21 | vars_starts_with(match, vars) 22 | 23 | vars_matches(match, vars) 24 | } 25 | \arguments{ 26 | \item{vars}{A character vector of variable names (taken from the selection context)} 27 | 28 | \item{match}{A character vector to match against} 29 | } 30 | \value{ 31 | A selection context 32 | } 33 | \description{ 34 | The output task allows to select model variables using 35 | a concise mini language. You can select variables by 36 | name or using one of the helper functions described below. 37 | \subsection{Overview of selection features}{ 38 | 39 | The selection of variables builds on the tidyselect package 40 | which implements a powerful variable selection language (see \link[tidyselect:language]{tidyselect::language}). 41 | The following features are most relevant for the 42 | selection of model variables: 43 | \itemize{ 44 | \item \code{|} for selecting the union of several variables 45 | \item \code{c()} for combining selections 46 | \item \code{!} for taking the complement of a set of variables 47 | } 48 | 49 | In addition, you can select variables using a combination of the following helper functions: 50 | \itemize{ 51 | \item \code{vars_prms()} selects all model parameters 52 | \item \code{vars_data()} selects all data defined variables 53 | \item \code{vars_eta()} selects all eta variables 54 | \item \code{vars_nm_std()} selects the standard NONMEM variables DV, PRED, RES, WRES, IPREDI, IWRESI 55 | \item \code{vars_starts_with()} selects variables that start with a prefix 56 | \item \code{vars_matches()} selects variables that match a regular expression 57 | } 58 | } 59 | } 60 | \examples{ 61 | 62 | m <- model() + 63 | input_variable("dose") + 64 | prm_log_normal("emax", median = 10, var_log = 0.09) + 65 | prm_log_normal("ed50", median = 50, var_log = 0.09) + 66 | algebraic(effect~emax*dose/(ed50 + dose)) + 67 | obs_proportional(~effect, var_prop = 1) 68 | 69 | # output all model parameter and eta variables 70 | render(m, tasks = tsk_output("prms", variables = vars_prms() | vars_eta())) 71 | } 72 | -------------------------------------------------------------------------------- /man/model.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/model.R 3 | \name{model} 4 | \alias{model} 5 | \title{General model} 6 | \usage{ 7 | model() 8 | } 9 | \value{ 10 | A general pharmacometric model 11 | } 12 | \description{ 13 | This function creates the basis for a general pharmacometric model, a flexible but verbose model type. 14 | } 15 | \details{ 16 | The function creates the foundation for a general pharmacometric model to which different building blocks can be added. The following building 17 | blocks are relevant for this model type: 18 | \itemize{ 19 | \item Parameters: \link{prm_log_normal}, \link{prm_logit_normal}, \link{prm_no_var}, \link{prm_normal} 20 | \item Observations: \link{obs_additive}, \link{obs_combined}, \link{obs_proportional} 21 | \item Algebraic relationships: \link{algebraic} 22 | \item Compartments: \link{compartment} 23 | \item Flows: \link{flow} 24 | \item Input variables: \link{input_variable}, \link{dataset} 25 | } 26 | 27 | The more specialized \code{\link[=pk_model]{pk_model()}} is converted to a general model during the rendering process. 28 | } 29 | \examples{ 30 | m <- model() + 31 | input_variable("dose") + 32 | prm_log_normal("emax") + 33 | prm_log_normal("ed50") + 34 | obs_additive(eff~emax*dose/(ed50+dose)) 35 | render(m) 36 | } 37 | -------------------------------------------------------------------------------- /man/names-NamedFacet-method.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/facet.R 3 | \name{names,NamedFacet-method} 4 | \alias{names,NamedFacet-method} 5 | \title{Access facet names} 6 | \usage{ 7 | \S4method{names}{NamedFacet}(x) 8 | } 9 | \arguments{ 10 | \item{x}{a named facet} 11 | } 12 | \description{ 13 | Access facet names 14 | } 15 | \keyword{internal} 16 | -------------------------------------------------------------------------------- /man/new_declaration.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/declaration-creation.R 3 | \name{new_declaration} 4 | \alias{new_declaration} 5 | \title{`declaration` constructor} 6 | \usage{ 7 | new_declaration(identifier = list(), definition = list()) 8 | } 9 | \arguments{ 10 | \item{identifier}{List of expressions} 11 | 12 | \item{definition}{List of expressions} 13 | } 14 | \value{ 15 | An assemblerr_declaration object 16 | } 17 | \description{ 18 | The internal constructor for a declaration vector. The user-facing version is `declaration`. 19 | } 20 | \details{ 21 | The arguments `identifier` and `definition` are lists of R expressions. For `identifier` only symbols, array expressions 22 | (e.g., theta[1]), or NULL are permitted. 23 | } 24 | \keyword{internal} 25 | -------------------------------------------------------------------------------- /man/nm_model.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/nm_model.R 3 | \name{nm_model} 4 | \alias{nm_model} 5 | \title{NONMEM model} 6 | \usage{ 7 | nm_model() 8 | } 9 | \value{ 10 | An nm_model 11 | } 12 | \description{ 13 | \code{nm_model()} creates the foundation for a NONMEM model 14 | } 15 | \details{ 16 | This function creates a NONMEM model object, a software-specific version of the general 17 | \code{\link{model}}. Like for the general model,this function only creates the empty 18 | base object which then needs to be filled with components before it can be rendered. The 19 | following components can be added 20 | to a NONMEM model: 21 | } 22 | \keyword{internal} 23 | -------------------------------------------------------------------------------- /man/nm_pk.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/nm_model.R 3 | \name{nm_pk} 4 | \alias{nm_pk} 5 | \title{Create model code entry} 6 | \usage{ 7 | nm_pk(statement) 8 | } 9 | \arguments{ 10 | \item{statement}{Code statement} 11 | } 12 | \value{ 13 | A facet 14 | } 15 | \description{ 16 | Create model code entry 17 | } 18 | \keyword{internal} 19 | -------------------------------------------------------------------------------- /man/nm_theta.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/nm_model.R 3 | \name{nm_theta} 4 | \alias{nm_theta} 5 | \title{Create facet for initial values} 6 | \usage{ 7 | nm_theta(name, initial = 1, lbound = -Inf, ubound = Inf) 8 | } 9 | \arguments{ 10 | \item{name}{Parameter name} 11 | 12 | \item{initial}{Initial value} 13 | 14 | \item{lbound}{Lower bound} 15 | 16 | \item{ubound}{Upper bound} 17 | } 18 | \value{ 19 | A NONMEM Theta parameter 20 | } 21 | \description{ 22 | Create facet for initial values 23 | } 24 | \keyword{internal} 25 | -------------------------------------------------------------------------------- /man/obs_additive.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/observation.R 3 | \name{obs_additive} 4 | \alias{obs_additive} 5 | \title{Observation with additive error} 6 | \usage{ 7 | obs_additive(prediction, name, var_add = 1) 8 | } 9 | \arguments{ 10 | \item{prediction}{A definition of the model prediction} 11 | 12 | \item{name}{A name for the observation (automatically derived if missing)} 13 | 14 | \item{var_add}{Variance of the additive error} 15 | } 16 | \value{ 17 | A building block of type 'observation' 18 | } 19 | \description{ 20 | This building block declares an observation model with an additive residual error model (\eqn{y = f + \epsilon_1}). 21 | } 22 | \details{ 23 | Observation models specify the observed variable, how an observation is 24 | expected to diverge from the model (i.e, the residual unexplained 25 | variability model), and parameter values. The observation model type is 26 | selected through the function name. The observed variable as well as the 27 | parameters are specified as function arguments. 28 | \subsection{Specifying predictions}{ 29 | 30 | The actual prediction from the model is the first argument of the 31 | function. It can be specified in a number of different ways: 32 | \itemize{ 33 | \item A name of a variable in the model: \code{obs_additive("effect")} 34 | \item A compartment concentration: \code{obs_additive(~C["central"])} 35 | \item An equation: \code{obs_additive(~base+slp*time)} 36 | } 37 | 38 | If the definition contains a variable name on the left-hand side (as in 39 | \code{conc~C["central"]}), the variable will appear in the generated model 40 | code. This can be useful to make the model code more readable if the 41 | prediction is defined as a long equation. 42 | } 43 | 44 | \subsection{Observation names}{ 45 | 46 | The observation name can be specified via the \verb{name=} argument and is 47 | automatically derived if the argument is left empty. Adding an 48 | observation model with an already existing name will replace the 49 | previous definition. 50 | } 51 | 52 | \subsection{Error variance}{ 53 | 54 | The variance of the error components are specified via the \verb{var_add=} 55 | and \verb{var_prop=} arguments of the function. 56 | } 57 | } 58 | \examples{ 59 | # additve RUV model for observing the variable WT 60 | m <- model() + 61 | prm_log_normal("wt") + 62 | obs_additive(~wt) 63 | 64 | # EMAX dose-response model with proportional RUV 65 | m2 <- model() + 66 | input_variable("dose") + 67 | prm_no_var("emax") + 68 | prm_no_var("ed50") + 69 | obs_proportional(effect~emax*dose/(ed50+dose)) 70 | } 71 | \seealso{ 72 | Other observation models: 73 | \code{\link{obs_combined}()}, 74 | \code{\link{obs_proportional}()} 75 | } 76 | \concept{observation models} 77 | -------------------------------------------------------------------------------- /man/obs_combined.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/observation.R 3 | \name{obs_combined} 4 | \alias{obs_combined} 5 | \title{Observation with combined error} 6 | \usage{ 7 | obs_combined(prediction, name, var_prop = 0.1, var_add = 1) 8 | } 9 | \arguments{ 10 | \item{prediction}{A definition of the model prediction} 11 | 12 | \item{name}{A name for the observation (automatically derived if missing)} 13 | 14 | \item{var_prop}{Variance of the proportional error component} 15 | 16 | \item{var_add}{Variance of the additive error component} 17 | } 18 | \value{ 19 | A building block of type 'observation' 20 | } 21 | \description{ 22 | This building block declares an observation model with a combined residual error model (\eqn{y = f + f \epsilon_1 + \epsilon_2}). 23 | } 24 | \details{ 25 | Observation models specify the observed variable, how an observation is 26 | expected to diverge from the model (i.e, the residual unexplained 27 | variability model), and parameter values. The observation model type is 28 | selected through the function name. The observed variable as well as the 29 | parameters are specified as function arguments. 30 | \subsection{Specifying predictions}{ 31 | 32 | The actual prediction from the model is the first argument of the 33 | function. It can be specified in a number of different ways: 34 | \itemize{ 35 | \item A name of a variable in the model: \code{obs_additive("effect")} 36 | \item A compartment concentration: \code{obs_additive(~C["central"])} 37 | \item An equation: \code{obs_additive(~base+slp*time)} 38 | } 39 | 40 | If the definition contains a variable name on the left-hand side (as in 41 | \code{conc~C["central"]}), the variable will appear in the generated model 42 | code. This can be useful to make the model code more readable if the 43 | prediction is defined as a long equation. 44 | } 45 | 46 | \subsection{Observation names}{ 47 | 48 | The observation name can be specified via the \verb{name=} argument and is 49 | automatically derived if the argument is left empty. Adding an 50 | observation model with an already existing name will replace the 51 | previous definition. 52 | } 53 | 54 | \subsection{Error variance}{ 55 | 56 | The variance of the error components are specified via the \verb{var_add=} 57 | and \verb{var_prop=} arguments of the function. 58 | } 59 | } 60 | \examples{ 61 | # additve RUV model for observing the variable WT 62 | m <- model() + 63 | prm_log_normal("wt") + 64 | obs_additive(~wt) 65 | 66 | # EMAX dose-response model with proportional RUV 67 | m2 <- model() + 68 | input_variable("dose") + 69 | prm_no_var("emax") + 70 | prm_no_var("ed50") + 71 | obs_proportional(effect~emax*dose/(ed50+dose)) 72 | } 73 | \seealso{ 74 | Other observation models: 75 | \code{\link{obs_additive}()}, 76 | \code{\link{obs_proportional}()} 77 | } 78 | \concept{observation models} 79 | -------------------------------------------------------------------------------- /man/obs_proportional.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/observation.R 3 | \name{obs_proportional} 4 | \alias{obs_proportional} 5 | \title{Observation with proportional error} 6 | \usage{ 7 | obs_proportional(prediction, name, var_prop = 0.1) 8 | } 9 | \arguments{ 10 | \item{prediction}{A definition of the model prediction} 11 | 12 | \item{name}{A name for the observation (automatically derived if missing)} 13 | 14 | \item{var_prop}{Variance of the proportional error} 15 | } 16 | \value{ 17 | A building block of type 'observation' 18 | } 19 | \description{ 20 | This building block declares an observation model with a proportional residual error model (\eqn{y = f + f \epsilon_1}). 21 | } 22 | \details{ 23 | Observation models specify the observed variable, how an observation is 24 | expected to diverge from the model (i.e, the residual unexplained 25 | variability model), and parameter values. The observation model type is 26 | selected through the function name. The observed variable as well as the 27 | parameters are specified as function arguments. 28 | \subsection{Specifying predictions}{ 29 | 30 | The actual prediction from the model is the first argument of the 31 | function. It can be specified in a number of different ways: 32 | \itemize{ 33 | \item A name of a variable in the model: \code{obs_additive("effect")} 34 | \item A compartment concentration: \code{obs_additive(~C["central"])} 35 | \item An equation: \code{obs_additive(~base+slp*time)} 36 | } 37 | 38 | If the definition contains a variable name on the left-hand side (as in 39 | \code{conc~C["central"]}), the variable will appear in the generated model 40 | code. This can be useful to make the model code more readable if the 41 | prediction is defined as a long equation. 42 | } 43 | 44 | \subsection{Observation names}{ 45 | 46 | The observation name can be specified via the \verb{name=} argument and is 47 | automatically derived if the argument is left empty. Adding an 48 | observation model with an already existing name will replace the 49 | previous definition. 50 | } 51 | 52 | \subsection{Error variance}{ 53 | 54 | The variance of the error components are specified via the \verb{var_add=} 55 | and \verb{var_prop=} arguments of the function. 56 | } 57 | } 58 | \examples{ 59 | # additve RUV model for observing the variable WT 60 | m <- model() + 61 | prm_log_normal("wt") + 62 | obs_additive(~wt) 63 | 64 | # EMAX dose-response model with proportional RUV 65 | m2 <- model() + 66 | input_variable("dose") + 67 | prm_no_var("emax") + 68 | prm_no_var("ed50") + 69 | obs_proportional(effect~emax*dose/(ed50+dose)) 70 | } 71 | \seealso{ 72 | Other observation models: 73 | \code{\link{obs_additive}()}, 74 | \code{\link{obs_combined}()} 75 | } 76 | \concept{observation models} 77 | -------------------------------------------------------------------------------- /man/pipe.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/assemblerr-package.R 3 | \name{\%>\%} 4 | \alias{\%>\%} 5 | \title{Pipe operator} 6 | \usage{ 7 | lhs \%>\% rhs 8 | } 9 | \description{ 10 | See \code{magrittr::\link[magrittr]{\%>\%}} for details. 11 | } 12 | \keyword{internal} 13 | -------------------------------------------------------------------------------- /man/pk_absorption_fo.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_absorption_fo} 4 | \alias{pk_absorption_fo} 5 | \title{PK absorption first-order} 6 | \usage{ 7 | pk_absorption_fo(prm_mat = prm_log_normal("mat", median = 0.5, var_log = 0.1)) 8 | } 9 | \arguments{ 10 | \item{prm_mat}{Parameter model for the mean absorption time (MAT)} 11 | } 12 | \value{ 13 | A building block of type 'pk_component' 14 | } 15 | \description{ 16 | This building block declares a first-order absorption component for a pharmacokinetic model. 17 | } 18 | \details{ 19 | \subsection{PK components}{ 20 | 21 | PK components can be added to a \link{pk_model} and exist in 22 | three different types: absorption, distribution, and elimination. The 23 | absorption component is optional, distribution and elimination are not 24 | and need to be added for the PK model to be valid. 25 | 26 | A PK model can only have one component of each type and adding a 27 | component with an already existing type will replace the previous 28 | definition. For example, the distribution component will be a two 29 | compartment model in the following snippet: 30 | 31 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 32 | pk_absorption_fo() + 33 | pk_distribution_1cmp() + 34 | pk_distribution_2cmp() + 35 | pk_elimination_linear() + 36 | obs_additive(conc~C["central"]) 37 | pkm 38 | }\if{html}{\out{
    }} 39 | } 40 | 41 | \subsection{Parameter models}{ 42 | 43 | All PK component functions allow the specification of the parameter 44 | model via their arguments. Arguments that refer to a parameter start 45 | with the prefix \code{prm_}. The default parameter model can be deduced from 46 | the default arguments in the usage section of the help entry. The 47 | parameter name, specified via the \verb{name=} argument of the parameter 48 | model building block allows the renaming of the model parameters. 49 | 50 | For example, the parameter \verb{prm_vc=} refers to the central volume of 51 | distribution parameter in the one compartment distribution PK component 52 | and the default parameter model is a log-normal distribution. The 53 | following code block specifies a normal distribution parameter model and 54 | names the parameter \code{v}: 55 | 56 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 57 | prm_vc = prm_normal("v", mean = 50, var = 25) 58 | ) 59 | }\if{html}{\out{
    }} 60 | } 61 | } 62 | \seealso{ 63 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 64 | 65 | Other absorption components: 66 | \code{\link{pk_absorption_fo_lag}()}, 67 | \code{\link{pk_absorption_fo_transit}()}, 68 | \code{\link{pk_absorption_fo_zo}()}, 69 | \code{\link{pk_absorption_zo_lag}()}, 70 | \code{\link{pk_absorption_zo}()} 71 | } 72 | \concept{absorption components} 73 | -------------------------------------------------------------------------------- /man/pk_absorption_fo_lag.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_absorption_fo_lag} 4 | \alias{pk_absorption_fo_lag} 5 | \title{PK absorption first-order, lag-time} 6 | \usage{ 7 | pk_absorption_fo_lag( 8 | prm_mat = prm_log_normal("mat", median = 0.5, var_log = 0.1), 9 | prm_mdt = prm_log_normal("mdt", median = 0.5, var_log = 0.1) 10 | ) 11 | } 12 | \arguments{ 13 | \item{prm_mat}{Parameter model for the mean absorption time (MAT)} 14 | 15 | \item{prm_mdt}{Parameter model for the mean delay time (MDT)} 16 | } 17 | \value{ 18 | A building block of type 'pk_component' 19 | } 20 | \description{ 21 | This building block declares a first-order absorption with lag-time component for a pharmacokinetic model. 22 | } 23 | \details{ 24 | \subsection{PK components}{ 25 | 26 | PK components can be added to a \link{pk_model} and exist in 27 | three different types: absorption, distribution, and elimination. The 28 | absorption component is optional, distribution and elimination are not 29 | and need to be added for the PK model to be valid. 30 | 31 | A PK model can only have one component of each type and adding a 32 | component with an already existing type will replace the previous 33 | definition. For example, the distribution component will be a two 34 | compartment model in the following snippet: 35 | 36 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 37 | pk_absorption_fo() + 38 | pk_distribution_1cmp() + 39 | pk_distribution_2cmp() + 40 | pk_elimination_linear() + 41 | obs_additive(conc~C["central"]) 42 | pkm 43 | }\if{html}{\out{
    }} 44 | } 45 | 46 | \subsection{Parameter models}{ 47 | 48 | All PK component functions allow the specification of the parameter 49 | model via their arguments. Arguments that refer to a parameter start 50 | with the prefix \code{prm_}. The default parameter model can be deduced from 51 | the default arguments in the usage section of the help entry. The 52 | parameter name, specified via the \verb{name=} argument of the parameter 53 | model building block allows the renaming of the model parameters. 54 | 55 | For example, the parameter \verb{prm_vc=} refers to the central volume of 56 | distribution parameter in the one compartment distribution PK component 57 | and the default parameter model is a log-normal distribution. The 58 | following code block specifies a normal distribution parameter model and 59 | names the parameter \code{v}: 60 | 61 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 62 | prm_vc = prm_normal("v", mean = 50, var = 25) 63 | ) 64 | }\if{html}{\out{
    }} 65 | } 66 | } 67 | \seealso{ 68 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 69 | 70 | Other absorption components: 71 | \code{\link{pk_absorption_fo_transit}()}, 72 | \code{\link{pk_absorption_fo_zo}()}, 73 | \code{\link{pk_absorption_fo}()}, 74 | \code{\link{pk_absorption_zo_lag}()}, 75 | \code{\link{pk_absorption_zo}()} 76 | } 77 | \concept{absorption components} 78 | -------------------------------------------------------------------------------- /man/pk_absorption_fo_transit.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_absorption_fo_transit} 4 | \alias{pk_absorption_fo_transit} 5 | \title{PK absorption first-order, transit compartment} 6 | \usage{ 7 | pk_absorption_fo_transit( 8 | prm_mat = prm_log_normal("mat", median = 0.5, var_log = 0.1), 9 | transit_compartments = 1L, 10 | prm_mdt = prm_log_normal("mdt", median = 0.5, var_log = 0.1) 11 | ) 12 | } 13 | \arguments{ 14 | \item{prm_mat}{Parameter model for the mean absorption time (MAT)} 15 | 16 | \item{transit_compartments}{Number of transit compartments} 17 | 18 | \item{prm_mdt}{Parameter model for the mean delay time (MDT)} 19 | } 20 | \value{ 21 | A building block of type 'pk_component' 22 | } 23 | \description{ 24 | This building block declares a first-order absorption with transit compartments component for 25 | a pharmacokinetic model. 26 | } 27 | \details{ 28 | \subsection{PK components}{ 29 | 30 | PK components can be added to a \link{pk_model} and exist in 31 | three different types: absorption, distribution, and elimination. The 32 | absorption component is optional, distribution and elimination are not 33 | and need to be added for the PK model to be valid. 34 | 35 | A PK model can only have one component of each type and adding a 36 | component with an already existing type will replace the previous 37 | definition. For example, the distribution component will be a two 38 | compartment model in the following snippet: 39 | 40 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 41 | pk_absorption_fo() + 42 | pk_distribution_1cmp() + 43 | pk_distribution_2cmp() + 44 | pk_elimination_linear() + 45 | obs_additive(conc~C["central"]) 46 | pkm 47 | }\if{html}{\out{
    }} 48 | } 49 | 50 | \subsection{Parameter models}{ 51 | 52 | All PK component functions allow the specification of the parameter 53 | model via their arguments. Arguments that refer to a parameter start 54 | with the prefix \code{prm_}. The default parameter model can be deduced from 55 | the default arguments in the usage section of the help entry. The 56 | parameter name, specified via the \verb{name=} argument of the parameter 57 | model building block allows the renaming of the model parameters. 58 | 59 | For example, the parameter \verb{prm_vc=} refers to the central volume of 60 | distribution parameter in the one compartment distribution PK component 61 | and the default parameter model is a log-normal distribution. The 62 | following code block specifies a normal distribution parameter model and 63 | names the parameter \code{v}: 64 | 65 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 66 | prm_vc = prm_normal("v", mean = 50, var = 25) 67 | ) 68 | }\if{html}{\out{
    }} 69 | } 70 | } 71 | \seealso{ 72 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 73 | 74 | Other absorption components: 75 | \code{\link{pk_absorption_fo_lag}()}, 76 | \code{\link{pk_absorption_fo_zo}()}, 77 | \code{\link{pk_absorption_fo}()}, 78 | \code{\link{pk_absorption_zo_lag}()}, 79 | \code{\link{pk_absorption_zo}()} 80 | } 81 | \concept{absorption components} 82 | -------------------------------------------------------------------------------- /man/pk_absorption_fo_zo.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_absorption_fo_zo} 4 | \alias{pk_absorption_fo_zo} 5 | \title{PK absorption first-order, zero-order delay} 6 | \usage{ 7 | pk_absorption_fo_zo( 8 | prm_mat = prm_log_normal("mat", median = 0.5, var_log = 0.1), 9 | prm_mdt = prm_log_normal("mdt", median = 0.5, var_log = 0.1) 10 | ) 11 | } 12 | \arguments{ 13 | \item{prm_mat}{Parameter model for the mean absorption time (MAT)} 14 | 15 | \item{prm_mdt}{Parameter model for the mean delay time (MDT)} 16 | } 17 | \value{ 18 | A building block of type 'pk_component' 19 | } 20 | \description{ 21 | This building block declares a first-order absorption with zero-order delay component 22 | for a pharmacokinetic model. 23 | } 24 | \details{ 25 | \subsection{PK components}{ 26 | 27 | PK components can be added to a \link{pk_model} and exist in 28 | three different types: absorption, distribution, and elimination. The 29 | absorption component is optional, distribution and elimination are not 30 | and need to be added for the PK model to be valid. 31 | 32 | A PK model can only have one component of each type and adding a 33 | component with an already existing type will replace the previous 34 | definition. For example, the distribution component will be a two 35 | compartment model in the following snippet: 36 | 37 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 38 | pk_absorption_fo() + 39 | pk_distribution_1cmp() + 40 | pk_distribution_2cmp() + 41 | pk_elimination_linear() + 42 | obs_additive(conc~C["central"]) 43 | pkm 44 | }\if{html}{\out{
    }} 45 | } 46 | 47 | \subsection{Parameter models}{ 48 | 49 | All PK component functions allow the specification of the parameter 50 | model via their arguments. Arguments that refer to a parameter start 51 | with the prefix \code{prm_}. The default parameter model can be deduced from 52 | the default arguments in the usage section of the help entry. The 53 | parameter name, specified via the \verb{name=} argument of the parameter 54 | model building block allows the renaming of the model parameters. 55 | 56 | For example, the parameter \verb{prm_vc=} refers to the central volume of 57 | distribution parameter in the one compartment distribution PK component 58 | and the default parameter model is a log-normal distribution. The 59 | following code block specifies a normal distribution parameter model and 60 | names the parameter \code{v}: 61 | 62 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 63 | prm_vc = prm_normal("v", mean = 50, var = 25) 64 | ) 65 | }\if{html}{\out{
    }} 66 | } 67 | } 68 | \seealso{ 69 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 70 | 71 | Other absorption components: 72 | \code{\link{pk_absorption_fo_lag}()}, 73 | \code{\link{pk_absorption_fo_transit}()}, 74 | \code{\link{pk_absorption_fo}()}, 75 | \code{\link{pk_absorption_zo_lag}()}, 76 | \code{\link{pk_absorption_zo}()} 77 | } 78 | \concept{absorption components} 79 | -------------------------------------------------------------------------------- /man/pk_absorption_zo.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_absorption_zo} 4 | \alias{pk_absorption_zo} 5 | \title{PK absorption zero-order} 6 | \usage{ 7 | pk_absorption_zo(prm_mat = prm_log_normal("mat", median = 0.5, var_log = 0.1)) 8 | } 9 | \arguments{ 10 | \item{prm_mat}{Parameter model for the mean absorption time (MAT)} 11 | } 12 | \value{ 13 | A building block of type 'pk_component' 14 | } 15 | \description{ 16 | This building block declares a zero-order absorption component for 17 | a pharmacokinetic model. 18 | } 19 | \details{ 20 | \subsection{PK components}{ 21 | 22 | PK components can be added to a \link{pk_model} and exist in 23 | three different types: absorption, distribution, and elimination. The 24 | absorption component is optional, distribution and elimination are not 25 | and need to be added for the PK model to be valid. 26 | 27 | A PK model can only have one component of each type and adding a 28 | component with an already existing type will replace the previous 29 | definition. For example, the distribution component will be a two 30 | compartment model in the following snippet: 31 | 32 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 33 | pk_absorption_fo() + 34 | pk_distribution_1cmp() + 35 | pk_distribution_2cmp() + 36 | pk_elimination_linear() + 37 | obs_additive(conc~C["central"]) 38 | pkm 39 | }\if{html}{\out{
    }} 40 | } 41 | 42 | \subsection{Parameter models}{ 43 | 44 | All PK component functions allow the specification of the parameter 45 | model via their arguments. Arguments that refer to a parameter start 46 | with the prefix \code{prm_}. The default parameter model can be deduced from 47 | the default arguments in the usage section of the help entry. The 48 | parameter name, specified via the \verb{name=} argument of the parameter 49 | model building block allows the renaming of the model parameters. 50 | 51 | For example, the parameter \verb{prm_vc=} refers to the central volume of 52 | distribution parameter in the one compartment distribution PK component 53 | and the default parameter model is a log-normal distribution. The 54 | following code block specifies a normal distribution parameter model and 55 | names the parameter \code{v}: 56 | 57 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 58 | prm_vc = prm_normal("v", mean = 50, var = 25) 59 | ) 60 | }\if{html}{\out{
    }} 61 | } 62 | } 63 | \seealso{ 64 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 65 | 66 | Other absorption components: 67 | \code{\link{pk_absorption_fo_lag}()}, 68 | \code{\link{pk_absorption_fo_transit}()}, 69 | \code{\link{pk_absorption_fo_zo}()}, 70 | \code{\link{pk_absorption_fo}()}, 71 | \code{\link{pk_absorption_zo_lag}()} 72 | } 73 | \concept{absorption components} 74 | -------------------------------------------------------------------------------- /man/pk_absorption_zo_lag.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_absorption_zo_lag} 4 | \alias{pk_absorption_zo_lag} 5 | \title{PK absorption zero-order, lag-time} 6 | \usage{ 7 | pk_absorption_zo_lag( 8 | prm_mat = prm_log_normal("mat", median = 0.5, var_log = 0.1), 9 | prm_mdt = prm_log_normal("mdt", median = 0.5, var_log = 0.1) 10 | ) 11 | } 12 | \arguments{ 13 | \item{prm_mat}{Parameter model for the mean absorption time (MAT)} 14 | 15 | \item{prm_mdt}{Parameter model for the mean delay time (MDT)} 16 | } 17 | \value{ 18 | A building block of type 'pk_component' 19 | } 20 | \description{ 21 | This building block declares a zero-order absorption with lag-time component for a pharmacokinetic model. 22 | } 23 | \details{ 24 | \subsection{PK components}{ 25 | 26 | PK components can be added to a \link{pk_model} and exist in 27 | three different types: absorption, distribution, and elimination. The 28 | absorption component is optional, distribution and elimination are not 29 | and need to be added for the PK model to be valid. 30 | 31 | A PK model can only have one component of each type and adding a 32 | component with an already existing type will replace the previous 33 | definition. For example, the distribution component will be a two 34 | compartment model in the following snippet: 35 | 36 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 37 | pk_absorption_fo() + 38 | pk_distribution_1cmp() + 39 | pk_distribution_2cmp() + 40 | pk_elimination_linear() + 41 | obs_additive(conc~C["central"]) 42 | pkm 43 | }\if{html}{\out{
    }} 44 | } 45 | 46 | \subsection{Parameter models}{ 47 | 48 | All PK component functions allow the specification of the parameter 49 | model via their arguments. Arguments that refer to a parameter start 50 | with the prefix \code{prm_}. The default parameter model can be deduced from 51 | the default arguments in the usage section of the help entry. The 52 | parameter name, specified via the \verb{name=} argument of the parameter 53 | model building block allows the renaming of the model parameters. 54 | 55 | For example, the parameter \verb{prm_vc=} refers to the central volume of 56 | distribution parameter in the one compartment distribution PK component 57 | and the default parameter model is a log-normal distribution. The 58 | following code block specifies a normal distribution parameter model and 59 | names the parameter \code{v}: 60 | 61 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 62 | prm_vc = prm_normal("v", mean = 50, var = 25) 63 | ) 64 | }\if{html}{\out{
    }} 65 | } 66 | } 67 | \seealso{ 68 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 69 | 70 | Other absorption components: 71 | \code{\link{pk_absorption_fo_lag}()}, 72 | \code{\link{pk_absorption_fo_transit}()}, 73 | \code{\link{pk_absorption_fo_zo}()}, 74 | \code{\link{pk_absorption_fo}()}, 75 | \code{\link{pk_absorption_zo}()} 76 | } 77 | \concept{absorption components} 78 | -------------------------------------------------------------------------------- /man/pk_distribution_1cmp.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_distribution_1cmp} 4 | \alias{pk_distribution_1cmp} 5 | \title{PK distribution 1 compartment} 6 | \usage{ 7 | pk_distribution_1cmp( 8 | prm_vc = prm_log_normal("vc", median = 100, var_log = 0.1) 9 | ) 10 | } 11 | \arguments{ 12 | \item{prm_vc}{Parameter model for the central volume of distribution} 13 | } 14 | \value{ 15 | A building block of type 'pk_component' 16 | } 17 | \description{ 18 | This building block declares a one compartment distribution component for a pharmacokinetic model. 19 | } 20 | \details{ 21 | \subsection{PK components}{ 22 | 23 | PK components can be added to a \link{pk_model} and exist in 24 | three different types: absorption, distribution, and elimination. The 25 | absorption component is optional, distribution and elimination are not 26 | and need to be added for the PK model to be valid. 27 | 28 | A PK model can only have one component of each type and adding a 29 | component with an already existing type will replace the previous 30 | definition. For example, the distribution component will be a two 31 | compartment model in the following snippet: 32 | 33 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 34 | pk_absorption_fo() + 35 | pk_distribution_1cmp() + 36 | pk_distribution_2cmp() + 37 | pk_elimination_linear() + 38 | obs_additive(conc~C["central"]) 39 | pkm 40 | }\if{html}{\out{
    }} 41 | } 42 | 43 | \subsection{Parameter models}{ 44 | 45 | All PK component functions allow the specification of the parameter 46 | model via their arguments. Arguments that refer to a parameter start 47 | with the prefix \code{prm_}. The default parameter model can be deduced from 48 | the default arguments in the usage section of the help entry. The 49 | parameter name, specified via the \verb{name=} argument of the parameter 50 | model building block allows the renaming of the model parameters. 51 | 52 | For example, the parameter \verb{prm_vc=} refers to the central volume of 53 | distribution parameter in the one compartment distribution PK component 54 | and the default parameter model is a log-normal distribution. The 55 | following code block specifies a normal distribution parameter model and 56 | names the parameter \code{v}: 57 | 58 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 59 | prm_vc = prm_normal("v", mean = 50, var = 25) 60 | ) 61 | }\if{html}{\out{
    }} 62 | } 63 | } 64 | \seealso{ 65 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 66 | 67 | Other distribution components: 68 | \code{\link{pk_distribution_2cmp}()}, 69 | \code{\link{pk_distribution_3cmp}()} 70 | } 71 | \concept{distribution components} 72 | -------------------------------------------------------------------------------- /man/pk_distribution_2cmp.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_distribution_2cmp} 4 | \alias{pk_distribution_2cmp} 5 | \title{PK distribution 2 compartments} 6 | \usage{ 7 | pk_distribution_2cmp( 8 | prm_vc = prm_log_normal("vc", median = 100, var_log = 0.1), 9 | prm_vp = prm_log_normal("vp", median = 5, var_log = 0.1), 10 | prm_q = prm_log_normal("q", median = 50, var_log = 0.1) 11 | ) 12 | } 13 | \arguments{ 14 | \item{prm_vc}{Parameter model for the central volume of distribution} 15 | 16 | \item{prm_vp}{Parameter model for the peripheral volume of distribution} 17 | 18 | \item{prm_q}{Parameter model for the inter-compartmental clearance} 19 | } 20 | \value{ 21 | A building block of type 'pk_component' 22 | } 23 | \description{ 24 | This building block declares a two compartment distribution component for a pharmacokinetic model. 25 | } 26 | \details{ 27 | \subsection{PK components}{ 28 | 29 | PK components can be added to a \link{pk_model} and exist in 30 | three different types: absorption, distribution, and elimination. The 31 | absorption component is optional, distribution and elimination are not 32 | and need to be added for the PK model to be valid. 33 | 34 | A PK model can only have one component of each type and adding a 35 | component with an already existing type will replace the previous 36 | definition. For example, the distribution component will be a two 37 | compartment model in the following snippet: 38 | 39 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 40 | pk_absorption_fo() + 41 | pk_distribution_1cmp() + 42 | pk_distribution_2cmp() + 43 | pk_elimination_linear() + 44 | obs_additive(conc~C["central"]) 45 | pkm 46 | }\if{html}{\out{
    }} 47 | } 48 | 49 | \subsection{Parameter models}{ 50 | 51 | All PK component functions allow the specification of the parameter 52 | model via their arguments. Arguments that refer to a parameter start 53 | with the prefix \code{prm_}. The default parameter model can be deduced from 54 | the default arguments in the usage section of the help entry. The 55 | parameter name, specified via the \verb{name=} argument of the parameter 56 | model building block allows the renaming of the model parameters. 57 | 58 | For example, the parameter \verb{prm_vc=} refers to the central volume of 59 | distribution parameter in the one compartment distribution PK component 60 | and the default parameter model is a log-normal distribution. The 61 | following code block specifies a normal distribution parameter model and 62 | names the parameter \code{v}: 63 | 64 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 65 | prm_vc = prm_normal("v", mean = 50, var = 25) 66 | ) 67 | }\if{html}{\out{
    }} 68 | } 69 | } 70 | \seealso{ 71 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 72 | 73 | Other distribution components: 74 | \code{\link{pk_distribution_1cmp}()}, 75 | \code{\link{pk_distribution_3cmp}()} 76 | } 77 | \concept{distribution components} 78 | -------------------------------------------------------------------------------- /man/pk_distribution_3cmp.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_distribution_3cmp} 4 | \alias{pk_distribution_3cmp} 5 | \title{PK distribution 3 compartments} 6 | \usage{ 7 | pk_distribution_3cmp( 8 | prm_vc = prm_log_normal("vc", median = 100, var_log = 0.1), 9 | prm_vp1 = prm_log_normal("vp1", median = 5, var_log = 0.1), 10 | prm_vp2 = prm_log_normal("vp2", median = 5, var_log = 0.1), 11 | prm_q1 = prm_log_normal("q1", median = 25, var_log = 0.1), 12 | prm_q2 = prm_log_normal("q2", median = 25, var_log = 0.1) 13 | ) 14 | } 15 | \arguments{ 16 | \item{prm_vc}{Parameter model for the central volume of distribution} 17 | 18 | \item{prm_vp1}{Parameter model for the volume of the first peripheral compartment} 19 | 20 | \item{prm_vp2}{Parameter model for the volume of the second peripheral compartment} 21 | 22 | \item{prm_q1}{Parameter model for the inter-compartmental clearance between central and first peripheral compartment} 23 | 24 | \item{prm_q2}{Parameter model for the inter-compartmental clearance between central and second peripheral compartment} 25 | } 26 | \value{ 27 | A building block of type 'pk_component' 28 | } 29 | \description{ 30 | This building block declares a three compartment distribution component for a pharmacokinetic model. 31 | } 32 | \details{ 33 | \subsection{PK components}{ 34 | 35 | PK components can be added to a \link{pk_model} and exist in 36 | three different types: absorption, distribution, and elimination. The 37 | absorption component is optional, distribution and elimination are not 38 | and need to be added for the PK model to be valid. 39 | 40 | A PK model can only have one component of each type and adding a 41 | component with an already existing type will replace the previous 42 | definition. For example, the distribution component will be a two 43 | compartment model in the following snippet: 44 | 45 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 46 | pk_absorption_fo() + 47 | pk_distribution_1cmp() + 48 | pk_distribution_2cmp() + 49 | pk_elimination_linear() + 50 | obs_additive(conc~C["central"]) 51 | pkm 52 | }\if{html}{\out{
    }} 53 | } 54 | 55 | \subsection{Parameter models}{ 56 | 57 | All PK component functions allow the specification of the parameter 58 | model via their arguments. Arguments that refer to a parameter start 59 | with the prefix \code{prm_}. The default parameter model can be deduced from 60 | the default arguments in the usage section of the help entry. The 61 | parameter name, specified via the \verb{name=} argument of the parameter 62 | model building block allows the renaming of the model parameters. 63 | 64 | For example, the parameter \verb{prm_vc=} refers to the central volume of 65 | distribution parameter in the one compartment distribution PK component 66 | and the default parameter model is a log-normal distribution. The 67 | following code block specifies a normal distribution parameter model and 68 | names the parameter \code{v}: 69 | 70 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 71 | prm_vc = prm_normal("v", mean = 50, var = 25) 72 | ) 73 | }\if{html}{\out{
    }} 74 | } 75 | } 76 | \seealso{ 77 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 78 | 79 | Other distribution components: 80 | \code{\link{pk_distribution_1cmp}()}, 81 | \code{\link{pk_distribution_2cmp}()} 82 | } 83 | \concept{distribution components} 84 | -------------------------------------------------------------------------------- /man/pk_elimination_linear.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_elimination_linear} 4 | \alias{pk_elimination_linear} 5 | \title{PK elimination linear} 6 | \usage{ 7 | pk_elimination_linear( 8 | prm_cl = prm_log_normal("cl", median = 50, var_log = 0.1) 9 | ) 10 | } 11 | \arguments{ 12 | \item{prm_cl}{Parameter model for the clearance} 13 | } 14 | \value{ 15 | A building block of type 'pk_component' 16 | } 17 | \description{ 18 | This building block declares a linear elimination component for a pharmacokinetic model. 19 | } 20 | \details{ 21 | \subsection{PK components}{ 22 | 23 | PK components can be added to a \link{pk_model} and exist in 24 | three different types: absorption, distribution, and elimination. The 25 | absorption component is optional, distribution and elimination are not 26 | and need to be added for the PK model to be valid. 27 | 28 | A PK model can only have one component of each type and adding a 29 | component with an already existing type will replace the previous 30 | definition. For example, the distribution component will be a two 31 | compartment model in the following snippet: 32 | 33 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 34 | pk_absorption_fo() + 35 | pk_distribution_1cmp() + 36 | pk_distribution_2cmp() + 37 | pk_elimination_linear() + 38 | obs_additive(conc~C["central"]) 39 | pkm 40 | }\if{html}{\out{
    }} 41 | } 42 | 43 | \subsection{Parameter models}{ 44 | 45 | All PK component functions allow the specification of the parameter 46 | model via their arguments. Arguments that refer to a parameter start 47 | with the prefix \code{prm_}. The default parameter model can be deduced from 48 | the default arguments in the usage section of the help entry. The 49 | parameter name, specified via the \verb{name=} argument of the parameter 50 | model building block allows the renaming of the model parameters. 51 | 52 | For example, the parameter \verb{prm_vc=} refers to the central volume of 53 | distribution parameter in the one compartment distribution PK component 54 | and the default parameter model is a log-normal distribution. The 55 | following code block specifies a normal distribution parameter model and 56 | names the parameter \code{v}: 57 | 58 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 59 | prm_vc = prm_normal("v", mean = 50, var = 25) 60 | ) 61 | }\if{html}{\out{
    }} 62 | } 63 | } 64 | \seealso{ 65 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 66 | 67 | Other elimination components: 68 | \code{\link{pk_elimination_linear_nl}()}, 69 | \code{\link{pk_elimination_nl}()} 70 | } 71 | \concept{elimination components} 72 | -------------------------------------------------------------------------------- /man/pk_elimination_linear_nl.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_elimination_linear_nl} 4 | \alias{pk_elimination_linear_nl} 5 | \title{PK elimination linear & nonlinear} 6 | \usage{ 7 | pk_elimination_linear_nl( 8 | prm_cllin = prm_log_normal("cllin", median = 50, var_log = 0.1), 9 | prm_clmm = prm_log_normal("clmm", median = 25, var_log = 0.1), 10 | prm_km = prm_log_normal("km", median = 0.5, var_log = 0.1), 11 | prm_vmax = NULL 12 | ) 13 | } 14 | \arguments{ 15 | \item{prm_cllin}{Parameter model for the linear clearance} 16 | 17 | \item{prm_clmm}{Parameter model for the non-linear clearance} 18 | 19 | \item{prm_km}{Parameter model for KM (the half-maximal concentration)} 20 | 21 | \item{prm_vmax}{Parameter model for Vmax (the maximal elimination rate)} 22 | } 23 | \value{ 24 | A building block of type 'pk_component' 25 | } 26 | \description{ 27 | This building block declares a mixed linear and nonlinear elimination component for a pharmacokinetic model. 28 | } 29 | \details{ 30 | \subsection{PK components}{ 31 | 32 | PK components can be added to a \link{pk_model} and exist in 33 | three different types: absorption, distribution, and elimination. The 34 | absorption component is optional, distribution and elimination are not 35 | and need to be added for the PK model to be valid. 36 | 37 | A PK model can only have one component of each type and adding a 38 | component with an already existing type will replace the previous 39 | definition. For example, the distribution component will be a two 40 | compartment model in the following snippet: 41 | 42 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 43 | pk_absorption_fo() + 44 | pk_distribution_1cmp() + 45 | pk_distribution_2cmp() + 46 | pk_elimination_linear() + 47 | obs_additive(conc~C["central"]) 48 | pkm 49 | }\if{html}{\out{
    }} 50 | } 51 | 52 | \subsection{Parameter models}{ 53 | 54 | All PK component functions allow the specification of the parameter 55 | model via their arguments. Arguments that refer to a parameter start 56 | with the prefix \code{prm_}. The default parameter model can be deduced from 57 | the default arguments in the usage section of the help entry. The 58 | parameter name, specified via the \verb{name=} argument of the parameter 59 | model building block allows the renaming of the model parameters. 60 | 61 | For example, the parameter \verb{prm_vc=} refers to the central volume of 62 | distribution parameter in the one compartment distribution PK component 63 | and the default parameter model is a log-normal distribution. The 64 | following code block specifies a normal distribution parameter model and 65 | names the parameter \code{v}: 66 | 67 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 68 | prm_vc = prm_normal("v", mean = 50, var = 25) 69 | ) 70 | }\if{html}{\out{
    }} 71 | } 72 | } 73 | \seealso{ 74 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 75 | 76 | Other elimination components: 77 | \code{\link{pk_elimination_linear}()}, 78 | \code{\link{pk_elimination_nl}()} 79 | } 80 | \concept{elimination components} 81 | -------------------------------------------------------------------------------- /man/pk_elimination_nl.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_component.R 3 | \name{pk_elimination_nl} 4 | \alias{pk_elimination_nl} 5 | \title{PK elimination nonlinear} 6 | \usage{ 7 | pk_elimination_nl( 8 | prm_clmm = prm_log_normal("clmm", median = 25, var_log = 0.1), 9 | prm_km = prm_log_normal("km", median = 0.5, var_log = 0.1), 10 | prm_vmax = NULL 11 | ) 12 | } 13 | \arguments{ 14 | \item{prm_clmm}{Parameter model for the clearance} 15 | 16 | \item{prm_km}{Parameter model for KM (the half-maximal concentration)} 17 | 18 | \item{prm_vmax}{Parameter model for Vmax (the maximal elimination rate)} 19 | } 20 | \value{ 21 | A building block of type 'pk_component' 22 | } 23 | \description{ 24 | This building block declares a nonlinear elimination component for a pharmacokinetic model. 25 | } 26 | \details{ 27 | \subsection{PK components}{ 28 | 29 | PK components can be added to a \link{pk_model} and exist in 30 | three different types: absorption, distribution, and elimination. The 31 | absorption component is optional, distribution and elimination are not 32 | and need to be added for the PK model to be valid. 33 | 34 | A PK model can only have one component of each type and adding a 35 | component with an already existing type will replace the previous 36 | definition. For example, the distribution component will be a two 37 | compartment model in the following snippet: 38 | 39 | \if{html}{\out{
    }}\preformatted{pkm <- pk_model() + 40 | pk_absorption_fo() + 41 | pk_distribution_1cmp() + 42 | pk_distribution_2cmp() + 43 | pk_elimination_linear() + 44 | obs_additive(conc~C["central"]) 45 | pkm 46 | }\if{html}{\out{
    }} 47 | } 48 | 49 | \subsection{Parameter models}{ 50 | 51 | All PK component functions allow the specification of the parameter 52 | model via their arguments. Arguments that refer to a parameter start 53 | with the prefix \code{prm_}. The default parameter model can be deduced from 54 | the default arguments in the usage section of the help entry. The 55 | parameter name, specified via the \verb{name=} argument of the parameter 56 | model building block allows the renaming of the model parameters. 57 | 58 | For example, the parameter \verb{prm_vc=} refers to the central volume of 59 | distribution parameter in the one compartment distribution PK component 60 | and the default parameter model is a log-normal distribution. The 61 | following code block specifies a normal distribution parameter model and 62 | names the parameter \code{v}: 63 | 64 | \if{html}{\out{
    }}\preformatted{pk_distribution_1cmp( 65 | prm_vc = prm_normal("v", mean = 50, var = 25) 66 | ) 67 | }\if{html}{\out{
    }} 68 | } 69 | } 70 | \seealso{ 71 | \code{\link[=pk_model]{pk_model()}} for the creation of PK models 72 | 73 | Other elimination components: 74 | \code{\link{pk_elimination_linear_nl}()}, 75 | \code{\link{pk_elimination_linear}()} 76 | } 77 | \concept{elimination components} 78 | -------------------------------------------------------------------------------- /man/pk_model.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/pk_model.R 3 | \name{pk_model} 4 | \alias{pk_model} 5 | \title{Create a PK model} 6 | \usage{ 7 | pk_model() 8 | } 9 | \value{ 10 | A pk_model 11 | } 12 | \description{ 13 | This function creates the basis for a pharmacokinetic model. 14 | } 15 | \details{ 16 | The function creates the foundation for a pharmacokinetic model to which different building blocks can be added. 17 | The following building blocks are relevant for this model type: 18 | \itemize{ 19 | \item Parameters: \link{prm_log_normal}, \link{prm_logit_normal}, \link{prm_no_var}, \link{prm_normal} 20 | \item Observations: \link{obs_additive}, \link{obs_combined}, \link{obs_proportional} 21 | \item Algebraic relationships: \link{algebraic} 22 | \item PK components: \link{pk_absorption_fo}, \link{pk_absorption_fo_lag}, \link{pk_absorption_fo_transit}, \link{pk_absorption_fo_zo}, \link{pk_absorption_zo}, \link{pk_absorption_zo_lag}, \link{pk_distribution_1cmp}, \link{pk_distribution_2cmp}, \link{pk_distribution_3cmp}, \link{pk_elimination_linear}, \link{pk_elimination_linear_nl}, \link{pk_elimination_nl}, \link{pk_model} 23 | \item Input variables: \link{input_variable}, \link{dataset} 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /man/plus-BuildingBlock-BuildingBlock-method.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/facet.R 3 | \name{+,BuildingBlock,BuildingBlock-method} 4 | \alias{+,BuildingBlock,BuildingBlock-method} 5 | \title{Add building blocks} 6 | \usage{ 7 | \S4method{+}{BuildingBlock,BuildingBlock}(e1, e2) 8 | } 9 | \arguments{ 10 | \item{e1}{A building block} 11 | 12 | \item{e2}{A building block} 13 | } 14 | \description{ 15 | Add building blocks 16 | } 17 | \keyword{internal} 18 | -------------------------------------------------------------------------------- /man/plus-BuildingBlock-NULL-method.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/facet.R 3 | \name{+,BuildingBlock,NULL-method} 4 | \alias{+,BuildingBlock,NULL-method} 5 | \title{Add building blocks} 6 | \usage{ 7 | \S4method{+}{BuildingBlock,`NULL`}(e1, e2) 8 | } 9 | \arguments{ 10 | \item{e1}{A building block} 11 | 12 | \item{e2}{NULL} 13 | } 14 | \description{ 15 | Add building blocks 16 | } 17 | \keyword{internal} 18 | -------------------------------------------------------------------------------- /man/print_shortened_tree_description.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/description.R 3 | \name{print_shortened_tree_description} 4 | \alias{print_shortened_tree_description} 5 | \title{Print tree description in compact format} 6 | \usage{ 7 | print_shortened_tree_description( 8 | tree_description, 9 | type = "building block", 10 | show = "all", 11 | child_type = "entries", 12 | skip_root = TRUE 13 | ) 14 | } 15 | \arguments{ 16 | \item{tree_description}{A TreeDescription object} 17 | 18 | \item{type}{type label to print to console} 19 | 20 | \item{show}{which child nodes of the root to print or 'all' to print all} 21 | 22 | \item{child_type}{type label for child elements} 23 | 24 | \item{skip_root}{whether the root node should be printed} 25 | } 26 | \value{ 27 | The function prints to the console 28 | } 29 | \description{ 30 | Print tree description in compact format 31 | } 32 | \keyword{internal} 33 | -------------------------------------------------------------------------------- /man/prm_log_normal.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/parameter.R 3 | \name{prm_log_normal} 4 | \alias{prm_log_normal} 5 | \title{Parameter with log-normal distribution} 6 | \usage{ 7 | prm_log_normal(name, median = 1, var_log = 0.1) 8 | } 9 | \arguments{ 10 | \item{name}{Parameter name} 11 | 12 | \item{median}{Median (on the normal scale)} 13 | 14 | \item{var_log}{Variance on the log scale} 15 | } 16 | \value{ 17 | A building block of type 'parameter' 18 | } 19 | \description{ 20 | This building block declares a parameter model for a parameter that follows the normal distribution on the log scale. 21 | } 22 | \details{ 23 | Parameter models specify type, name, and values for a parameter. The 24 | parameter model type is selected through the function name. The 25 | parameter name and values are provided as function arguments. 26 | \subsection{Parameter names}{ 27 | 28 | Every parameter must have a valid name. A parameter name can contain 29 | letters, numbers as well as the underscore character. The name needs to 30 | start with a letter. 31 | 32 | Adding a parameter with an already existing name will replace the 33 | definition of the parameter. For example, the parameter “base” will have 34 | a log-normal distribution in the following snippet: 35 | 36 | \if{html}{\out{
    }}\preformatted{m <- model() + 37 | prm_normal("base") + 38 | prm_log_normal("base") 39 | }\if{html}{\out{
    }} 40 | } 41 | 42 | \subsection{Parameter values}{ 43 | 44 | The parameter values that a parameter model expects vary by type. For 45 | example, \code{prm_normal()} requires the mean and the variance, whereas for 46 | \code{prm_log_normal()} median and variance on the log scale need to be 47 | provided. The argument name should indicate what parameter value is 48 | expected. 49 | } 50 | 51 | \subsection{MU-referencing}{ 52 | 53 | \code{assemblerr} can include mu-referencing statements for parameter 54 | distributions that support it. The functionality can be activated by 55 | setting the option \code{prm.use_mu_referencing} to \code{TRUE} as shown in the 56 | following snippet: 57 | 58 | \if{html}{\out{
    }}\preformatted{m <- model() + 59 | prm_normal("base") + 60 | prm_log_normal("slp") + 61 | obs_additive(response~base+slp*time) 62 | 63 | render( 64 | model = m, 65 | options = assemblerr_options(prm.use_mu_referencing = TRUE) 66 | ) 67 | }\if{html}{\out{
    }} 68 | } 69 | } 70 | \examples{ 71 | # EMAX dose-response model with emax (log-normal) and ed50 (no variability) parameters 72 | m2 <- model() + 73 | input_variable("dose") + 74 | prm_log_normal("emax", 10, 0.3) + 75 | prm_no_var("ed50", 5) + 76 | obs_proportional(effect~emax*dose/(ed50+dose)) 77 | 78 | # a log-normal parameter that is directly observed 79 | m <- model() + 80 | prm_log_normal("wt") + 81 | obs_additive(~wt) 82 | 83 | } 84 | \seealso{ 85 | Other parameter models: 86 | \code{\link{prm_logit_normal}()}, 87 | \code{\link{prm_no_var}()}, 88 | \code{\link{prm_normal}()} 89 | } 90 | \concept{parameter models} 91 | -------------------------------------------------------------------------------- /man/prm_logit_normal.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/parameter.R 3 | \name{prm_logit_normal} 4 | \alias{prm_logit_normal} 5 | \title{Parameter with logit-normal distribution} 6 | \usage{ 7 | prm_logit_normal(name, mean_logit = 0, var_logit = 1) 8 | } 9 | \arguments{ 10 | \item{name}{Parameter name} 11 | 12 | \item{mean_logit}{Mean on the logit scale} 13 | 14 | \item{var_logit}{Variance on the logit scale} 15 | } 16 | \value{ 17 | A building block of type 'parameter' 18 | } 19 | \description{ 20 | This building block declares a parameter model for a parameter that follows the normal distribution on the logit-scale. 21 | } 22 | \details{ 23 | Parameter models specify type, name, and values for a parameter. The 24 | parameter model type is selected through the function name. The 25 | parameter name and values are provided as function arguments. 26 | \subsection{Parameter names}{ 27 | 28 | Every parameter must have a valid name. A parameter name can contain 29 | letters, numbers as well as the underscore character. The name needs to 30 | start with a letter. 31 | 32 | Adding a parameter with an already existing name will replace the 33 | definition of the parameter. For example, the parameter “base” will have 34 | a log-normal distribution in the following snippet: 35 | 36 | \if{html}{\out{
    }}\preformatted{m <- model() + 37 | prm_normal("base") + 38 | prm_log_normal("base") 39 | }\if{html}{\out{
    }} 40 | } 41 | 42 | \subsection{Parameter values}{ 43 | 44 | The parameter values that a parameter model expects vary by type. For 45 | example, \code{prm_normal()} requires the mean and the variance, whereas for 46 | \code{prm_log_normal()} median and variance on the log scale need to be 47 | provided. The argument name should indicate what parameter value is 48 | expected. 49 | } 50 | 51 | \subsection{MU-referencing}{ 52 | 53 | \code{assemblerr} can include mu-referencing statements for parameter 54 | distributions that support it. The functionality can be activated by 55 | setting the option \code{prm.use_mu_referencing} to \code{TRUE} as shown in the 56 | following snippet: 57 | 58 | \if{html}{\out{
    }}\preformatted{m <- model() + 59 | prm_normal("base") + 60 | prm_log_normal("slp") + 61 | obs_additive(response~base+slp*time) 62 | 63 | render( 64 | model = m, 65 | options = assemblerr_options(prm.use_mu_referencing = TRUE) 66 | ) 67 | }\if{html}{\out{
    }} 68 | } 69 | } 70 | \examples{ 71 | # EMAX dose-response model with emax (log-normal) and ed50 (no variability) parameters 72 | m2 <- model() + 73 | input_variable("dose") + 74 | prm_log_normal("emax", 10, 0.3) + 75 | prm_no_var("ed50", 5) + 76 | obs_proportional(effect~emax*dose/(ed50+dose)) 77 | 78 | # a log-normal parameter that is directly observed 79 | m <- model() + 80 | prm_log_normal("wt") + 81 | obs_additive(~wt) 82 | 83 | } 84 | \seealso{ 85 | Other parameter models: 86 | \code{\link{prm_log_normal}()}, 87 | \code{\link{prm_no_var}()}, 88 | \code{\link{prm_normal}()} 89 | } 90 | \concept{parameter models} 91 | -------------------------------------------------------------------------------- /man/prm_no_var.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/parameter.R 3 | \name{prm_no_var} 4 | \alias{prm_no_var} 5 | \title{Parameter without variability} 6 | \usage{ 7 | prm_no_var(name, value = 1) 8 | } 9 | \arguments{ 10 | \item{name}{Parameter name} 11 | 12 | \item{value}{Parameter value} 13 | } 14 | \value{ 15 | A building block of type 'parameter' 16 | } 17 | \description{ 18 | This building block declares a parameter model for a parameter that does not vary between subjects. 19 | } 20 | \details{ 21 | Parameter models specify type, name, and values for a parameter. The 22 | parameter model type is selected through the function name. The 23 | parameter name and values are provided as function arguments. 24 | \subsection{Parameter names}{ 25 | 26 | Every parameter must have a valid name. A parameter name can contain 27 | letters, numbers as well as the underscore character. The name needs to 28 | start with a letter. 29 | 30 | Adding a parameter with an already existing name will replace the 31 | definition of the parameter. For example, the parameter “base” will have 32 | a log-normal distribution in the following snippet: 33 | 34 | \if{html}{\out{
    }}\preformatted{m <- model() + 35 | prm_normal("base") + 36 | prm_log_normal("base") 37 | }\if{html}{\out{
    }} 38 | } 39 | 40 | \subsection{Parameter values}{ 41 | 42 | The parameter values that a parameter model expects vary by type. For 43 | example, \code{prm_normal()} requires the mean and the variance, whereas for 44 | \code{prm_log_normal()} median and variance on the log scale need to be 45 | provided. The argument name should indicate what parameter value is 46 | expected. 47 | } 48 | 49 | \subsection{MU-referencing}{ 50 | 51 | \code{assemblerr} can include mu-referencing statements for parameter 52 | distributions that support it. The functionality can be activated by 53 | setting the option \code{prm.use_mu_referencing} to \code{TRUE} as shown in the 54 | following snippet: 55 | 56 | \if{html}{\out{
    }}\preformatted{m <- model() + 57 | prm_normal("base") + 58 | prm_log_normal("slp") + 59 | obs_additive(response~base+slp*time) 60 | 61 | render( 62 | model = m, 63 | options = assemblerr_options(prm.use_mu_referencing = TRUE) 64 | ) 65 | }\if{html}{\out{
    }} 66 | } 67 | } 68 | \examples{ 69 | # EMAX dose-response model with emax (log-normal) and ed50 (no variability) parameters 70 | m2 <- model() + 71 | input_variable("dose") + 72 | prm_log_normal("emax", 10, 0.3) + 73 | prm_no_var("ed50", 5) + 74 | obs_proportional(effect~emax*dose/(ed50+dose)) 75 | 76 | # a log-normal parameter that is directly observed 77 | m <- model() + 78 | prm_log_normal("wt") + 79 | obs_additive(~wt) 80 | 81 | } 82 | \seealso{ 83 | Other parameter models: 84 | \code{\link{prm_log_normal}()}, 85 | \code{\link{prm_logit_normal}()}, 86 | \code{\link{prm_normal}()} 87 | } 88 | \concept{parameter models} 89 | -------------------------------------------------------------------------------- /man/prm_normal.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/parameter.R 3 | \name{prm_normal} 4 | \alias{prm_normal} 5 | \title{Parameter with normal distribution} 6 | \usage{ 7 | prm_normal(name, mean = 1, var = 0.1) 8 | } 9 | \arguments{ 10 | \item{name}{Parameter name} 11 | 12 | \item{mean}{Mean} 13 | 14 | \item{var}{Variance} 15 | } 16 | \value{ 17 | A building block of type 'parameter' 18 | } 19 | \description{ 20 | This building block declares a parameter model for a parameter that follows the normal distribution. 21 | } 22 | \details{ 23 | Parameter models specify type, name, and values for a parameter. The 24 | parameter model type is selected through the function name. The 25 | parameter name and values are provided as function arguments. 26 | \subsection{Parameter names}{ 27 | 28 | Every parameter must have a valid name. A parameter name can contain 29 | letters, numbers as well as the underscore character. The name needs to 30 | start with a letter. 31 | 32 | Adding a parameter with an already existing name will replace the 33 | definition of the parameter. For example, the parameter “base” will have 34 | a log-normal distribution in the following snippet: 35 | 36 | \if{html}{\out{
    }}\preformatted{m <- model() + 37 | prm_normal("base") + 38 | prm_log_normal("base") 39 | }\if{html}{\out{
    }} 40 | } 41 | 42 | \subsection{Parameter values}{ 43 | 44 | The parameter values that a parameter model expects vary by type. For 45 | example, \code{prm_normal()} requires the mean and the variance, whereas for 46 | \code{prm_log_normal()} median and variance on the log scale need to be 47 | provided. The argument name should indicate what parameter value is 48 | expected. 49 | } 50 | 51 | \subsection{MU-referencing}{ 52 | 53 | \code{assemblerr} can include mu-referencing statements for parameter 54 | distributions that support it. The functionality can be activated by 55 | setting the option \code{prm.use_mu_referencing} to \code{TRUE} as shown in the 56 | following snippet: 57 | 58 | \if{html}{\out{
    }}\preformatted{m <- model() + 59 | prm_normal("base") + 60 | prm_log_normal("slp") + 61 | obs_additive(response~base+slp*time) 62 | 63 | render( 64 | model = m, 65 | options = assemblerr_options(prm.use_mu_referencing = TRUE) 66 | ) 67 | }\if{html}{\out{
    }} 68 | } 69 | } 70 | \examples{ 71 | # EMAX dose-response model with emax (log-normal) and ed50 (no variability) parameters 72 | m2 <- model() + 73 | input_variable("dose") + 74 | prm_log_normal("emax", 10, 0.3) + 75 | prm_no_var("ed50", 5) + 76 | obs_proportional(effect~emax*dose/(ed50+dose)) 77 | 78 | # a log-normal parameter that is directly observed 79 | m <- model() + 80 | prm_log_normal("wt") + 81 | obs_additive(~wt) 82 | 83 | } 84 | \seealso{ 85 | Other parameter models: 86 | \code{\link{prm_log_normal}()}, 87 | \code{\link{prm_logit_normal}()}, 88 | \code{\link{prm_no_var}()} 89 | } 90 | \concept{parameter models} 91 | -------------------------------------------------------------------------------- /man/render.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/rendering.R 3 | \name{render} 4 | \alias{render} 5 | \title{Generate model code} 6 | \usage{ 7 | render( 8 | model, 9 | filename = NULL, 10 | target_tool = "nonmem", 11 | tasks = tsk_estimation(), 12 | options = assemblerr_options() 13 | ) 14 | } 15 | \arguments{ 16 | \item{model}{A model object} 17 | 18 | \item{filename}{Name of the model file to create or NULL} 19 | 20 | \item{target_tool}{Name of the target tool (currently only 'nonmem')} 21 | 22 | \item{tasks}{A task specification} 23 | 24 | \item{options}{List of options for model generation} 25 | } 26 | \value{ 27 | The model code as a character vector 28 | } 29 | \description{ 30 | This function generates the code for a model object, prints it to the console or writes it to a file. 31 | } 32 | \details{ 33 | The generated code will be written to the file specified by \verb{filename=} or printed to the console if the filename is 34 | set to \code{NULL}. Only \code{'nonmem'} is currently supported as a \verb{target_tool=} option. The \verb{tasks=} argument allows the 35 | specification of model tasks and the \verb{options=} argument customizes the generated code. 36 | \subsection{Task specification}{ 37 | 38 | Tasks are building blocks that allow to specify what a model should "do". Like other model building blocks, they can be combined using the \code{+} operator. 39 | For example, the following adds an estimation task and an xpose4 output task to the generated code: 40 | 41 | \if{html}{\out{
    }}\preformatted{ render(m, tasks = tsk_estimation() + 42 | tsk_output_xpose4()) 43 | }\if{html}{\out{
    }} 44 | 45 | The default argument (\code{tasks=tsk_estimation()}) adds an FOCE estimation task to the code. 46 | } 47 | 48 | \subsection{Rendering options}{ 49 | 50 | The \verb{options=} argument allows to modify the rendering process and, hence, the generated code. Options are provided 51 | as a list and the \code{assemblerr_options()} function helps to generate list with the proper formatting. 52 | 53 | The following code block renders the model \code{m} with automatic mu-referencing for the model parameters 54 | 55 | \if{html}{\out{
    }}\preformatted{ render(m, options = assemblerr_options(prm.use_mu_referencing = TRUE)) 56 | }\if{html}{\out{
    }} 57 | } 58 | } 59 | \examples{ 60 | m <- model() + 61 | input_variable("dose") + 62 | prm_log_normal("emax") + 63 | prm_log_normal("ed50") + 64 | obs_additive(eff~emax*dose/(ed50+dose)) 65 | # render to console 66 | render(m) 67 | 68 | # render to file 69 | \dontrun{ 70 | setwd(tempdir()) 71 | render(m, "run1.mod") 72 | } 73 | 74 | # render to console with estimation & output task 75 | render(m, tasks = tsk_estimation() + tsk_output_xpose4()) 76 | 77 | } 78 | -------------------------------------------------------------------------------- /man/rmd/observation-model.Rmd: -------------------------------------------------------------------------------- 1 | Observation models specify the observed variable, how an observation is expected to diverge from the model (i.e, the residual unexplained variability model), 2 | and parameter values. The observation model type is selected through the function name. The observed variable as well as the parameters are specified as function 3 | arguments. 4 | 5 | ## Specifying predictions 6 | 7 | The actual prediction from the model is the first argument of the function. It can be specified in a number of different ways: 8 | 9 | - A name of a variable in the model: `obs_additive("effect")` 10 | - A compartment concentration: `obs_additive(~C["central"])` 11 | - An equation: `obs_additive(~base+slp*time)` 12 | 13 | If the definition contains a variable name on the left-hand side (as in `conc~C["central"]`), the variable will appear in the generated model code. 14 | This can be useful to make the model code more readable if the prediction is defined as a long equation. 15 | 16 | ## Observation names 17 | 18 | The observation name can be specified via the `name=` argument and is automatically derived if the argument is left empty. Adding an observation model 19 | with an already existing name will replace the previous definition. 20 | 21 | ## Error variance 22 | 23 | The variance of the error components are specified via the `var_add=` and `var_prop=` arguments of the function. 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /man/rmd/parameter-model.Rmd: -------------------------------------------------------------------------------- 1 | Parameter models specify type, name, and values for a parameter. The parameter model type is selected through the function name. The parameter 2 | name and values are provided as function arguments. 3 | 4 | ## Parameter names 5 | 6 | Every parameter must have a valid name. A parameter name can contain letters, numbers as well as the underscore character. 7 | The name needs to start with a letter. 8 | 9 | Adding a parameter with an already existing name will replace the definition of the parameter. For example, the parameter "base" 10 | will have a log-normal distribution in the following snippet: 11 | 12 | ``` 13 | m <- model() + 14 | prm_normal("base") + 15 | prm_log_normal("base") 16 | ``` 17 | 18 | ## Parameter values 19 | 20 | The parameter values that a parameter model expects vary by type. For example, `prm_normal()` requires the mean and the variance, whereas for `prm_log_normal()` 21 | median and variance on the log scale need to be provided. The argument name should indicate what parameter value is expected. 22 | 23 | ## MU-referencing 24 | 25 | `assemblerr` can include mu-referencing statements for parameter distributions that support it. The functionality can be 26 | activated by setting the option `prm.use_mu_referencing` to `TRUE` as shown in the following snippet: 27 | 28 | ``` 29 | m <- model() + 30 | prm_normal("base") + 31 | prm_log_normal("slp") + 32 | obs_additive(response~base+slp*time) 33 | 34 | render( 35 | model = m, 36 | options = assemblerr_options(prm.use_mu_referencing = TRUE) 37 | ) 38 | ``` 39 | -------------------------------------------------------------------------------- /man/rmd/pk-component.Rmd: -------------------------------------------------------------------------------- 1 | ## PK components 2 | 3 | PK components can be added to a [pk_model] and exist in three different types: absorption, distribution, and elimination. 4 | The absorption component is optional, distribution and elimination are not and need to be added for the PK model to be valid. 5 | 6 | A PK model can only have one component of each type and adding a component with an already existing type will replace the previous definition. For example, the distribution component will be a two compartment model in the following snippet: 7 | 8 | ``` 9 | pkm <- pk_model() + 10 | pk_absorption_fo() + 11 | pk_distribution_1cmp() + 12 | pk_distribution_2cmp() + 13 | pk_elimination_linear() + 14 | obs_additive(conc~C["central"]) 15 | pkm 16 | ``` 17 | 18 | ## Parameter models 19 | 20 | All PK component functions allow the specification of the parameter model via their arguments. Arguments that refer to a 21 | parameter start with the prefix `prm_`. The default parameter model can be deduced from the default arguments in the usage section of the help entry. The parameter name, specified via the `name=` argument of the parameter model building block allows the renaming of the model parameters. 22 | 23 | For example, the parameter `prm_vc=` refers to the central volume of distribution parameter in the one compartment distribution PK component and the default parameter model is a log-normal distribution. The following code block specifies a normal distribution parameter model and names the parameter `v`: 24 | 25 | ``` 26 | pk_distribution_1cmp( 27 | prm_vc = prm_normal("v", mean = 50, var = 25) 28 | ) 29 | ``` 30 | -------------------------------------------------------------------------------- /man/rmd/tasks.Rmd: -------------------------------------------------------------------------------- 1 | ## Tasks 2 | 3 | Tasks are building blocks that allow to specify what a model should "do". Like other model building blocks, they can be combined using the `+` operator. However, they should not be added to a model but rather provided via the `tasks=` argument to the render function, e.g., 4 | 5 | ```r 6 | render(m, tasks = tsk_estimation() + 7 | tsk_output_xpose4()) 8 | ``` 9 | -------------------------------------------------------------------------------- /man/transform_ast.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/ast.R 3 | \name{transform_ast} 4 | \alias{transform_ast} 5 | \title{Modify AST} 6 | \usage{ 7 | transform_ast(node, transformer, ...) 8 | } 9 | \arguments{ 10 | \item{node}{A language node} 11 | 12 | \item{transformer}{A transformer function} 13 | 14 | \item{...}{Additional arguments to the transformer function} 15 | } 16 | \value{ 17 | The transformed language node 18 | } 19 | \description{ 20 | This recursive function is the work-horse for all expression transformations. It takes a language node and a transformer function, 21 | and applies the transformer recursivly to the node and all its child nodes. 22 | } 23 | \keyword{internal} 24 | -------------------------------------------------------------------------------- /man/tsk_output.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/tasks.R 3 | \name{tsk_output} 4 | \alias{tsk_output} 5 | \alias{tsk_output_xpose4} 6 | \title{Task output} 7 | \usage{ 8 | tsk_output(filename = "sdtab", variables) 9 | 10 | tsk_output_xpose4() 11 | } 12 | \arguments{ 13 | \item{filename}{The filename for the output file} 14 | 15 | \item{variables}{The model variables that be included in the output} 16 | } 17 | \value{ 18 | A building block of type 'output_task' 19 | } 20 | \description{ 21 | These functions define output tasks that include the selected variables in the output of the generated model. 22 | } 23 | \details{ 24 | \subsection{Tasks}{ 25 | 26 | Tasks are building blocks that allow to specify what a model should 27 | “do”. Like other model building blocks, they can be combined using 28 | the \code{+} operator. However, they should not be added to a model but 29 | rather provided via the \verb{tasks=} argument to the render function, e.g., 30 | 31 | \if{html}{\out{
    }}\preformatted{render(m, tasks = tsk_estimation() + 32 | tsk_output_xpose4()) 33 | }\if{html}{\out{
    }} 34 | } 35 | 36 | \subsection{Output tasks}{ 37 | 38 | For NONMEM, an output task defines the \verb{$TABLE} records by specifying the \verb{filename=} as well as the \verb{variables=} to include. 39 | 40 | The variables can be specified by providing a character vector of variable names (e.g., \code{variables = c('cl','v')}) or by 41 | using a set of variable selection helpers (e.g., \code{variables = vars_prms()}). The latter is shorter if many variables are to 42 | be selected and allows the specification of tasks independent from the model. The details of the variable selection language 43 | can be found on the help pages for \link{model-variable-selection}. 44 | } 45 | 46 | \subsection{xpose4 output task}{ 47 | 48 | The \code{tsk_output_xpose4()} function includes \verb{$TABLE} records that follow the output conventions of the model diagnostic package xpose4. 49 | It is a shortcut for the following two output tasks: 50 | 51 | \if{html}{\out{
    }}\preformatted{ xpose4_output <- tsk_output("sdtab", variables = any_of(c("id","time")) | vars_nm_std()) + 52 | tsk_output("patab", variables = vars_prms() | vars_eta()) 53 | }\if{html}{\out{
    }} 54 | } 55 | } 56 | \examples{ 57 | m <- model() + 58 | input_variable("dose") + 59 | prm_log_normal("emax", median = 10, var_log = 0.09) + 60 | prm_log_normal("ed50", median = 50, var_log = 0.09) + 61 | algebraic(effect~emax*dose/(ed50 + dose)) + 62 | obs_proportional(~effect, var_prop = 1) 63 | # output model parameters to file 'prms' 64 | render(m, tasks = tsk_output("prms", variables = vars_prms())) 65 | # output variables required by xpose4 66 | render(m, tasks = tsk_output_xpose4()) 67 | } 68 | \seealso{ 69 | Other tasks: 70 | \code{\link{tsk_estimation}()} 71 | } 72 | \concept{tasks} 73 | -------------------------------------------------------------------------------- /man/xtfrm-IssueList-method.Rd: -------------------------------------------------------------------------------- 1 | % Generated by roxygen2: do not edit by hand 2 | % Please edit documentation in R/issues.R 3 | \name{xtfrm,IssueList-method} 4 | \alias{xtfrm,IssueList-method} 5 | \title{Auxiliary Function for Sorting and Ranking} 6 | \usage{ 7 | \S4method{xtfrm}{IssueList}(x) 8 | } 9 | \arguments{ 10 | \item{x}{an R Object} 11 | } 12 | \description{ 13 | Auxiliary Function for Sorting and Ranking 14 | } 15 | \keyword{internal} 16 | -------------------------------------------------------------------------------- /renv/.gitignore: -------------------------------------------------------------------------------- 1 | local/ 2 | cellar/ 3 | lock/ 4 | library/ 5 | python/ 6 | staging/ 7 | -------------------------------------------------------------------------------- /tests/testthat.R: -------------------------------------------------------------------------------- 1 | library(testthat) 2 | library(assemblerr) 3 | 4 | test_check("assemblerr") 5 | -------------------------------------------------------------------------------- /tests/testthat/_snaps/issues.md: -------------------------------------------------------------------------------- 1 | # printing of issues 2 | 3 | Code 4 | print(issues) 5 | Message 6 | ! 2 issues (1 critical & 1 non-critical) 7 | 1. test2 8 | 2. test 9 | 10 | -------------------------------------------------------------------------------- /tests/testthat/_snaps/model.md: -------------------------------------------------------------------------------- 1 | # check empty model 2 | 3 | Code 4 | check(model()) 5 | Message 6 | ! 2 critical issues 7 | 1. No parameters specified 8 | 2. No observation specified 9 | 10 | # check simple model 11 | 12 | Code 13 | check(simple_model()) 14 | Message 15 | SUCCESS! No issues 16 | 17 | -------------------------------------------------------------------------------- /tests/testthat/_snaps/pk-model.md: -------------------------------------------------------------------------------- 1 | # check empty pk_model 2 | 3 | Code 4 | check(pk_model()) 5 | Message 6 | ! 4 critical issues 7 | 1. No parameters specified 8 | 2. A distribution component is missing 9 | 3. An elimination component is missing 10 | 4. No observation specified 11 | 12 | # check complete pk_model 13 | 14 | Code 15 | check(pk_model() + pk_distribution_1cmp() + pk_elimination_linear() + 16 | obs_additive(conc ~ C["central"])) 17 | Message 18 | SUCCESS! No issues 19 | 20 | -------------------------------------------------------------------------------- /tests/testthat/integration-tests/test-nonmem-integration.R: -------------------------------------------------------------------------------- 1 | context("nonmem-integration") 2 | 3 | skip_on_cran() 4 | # check if PsN is available 5 | skip_if_not(system("psn -version", intern = FALSE, ignore.stdout = TRUE) == 0, "PsN installation not found.") 6 | 7 | 8 | test_nm_model_execution <- function(model, options = assemblerr_options(), debug = FALSE, env = parent.frame()) { 9 | local_create_nonmem_test_directory(debug = debug, env = env) 10 | create_dummy_data(model, path = "data.csv") 11 | render(model, "run1.mod", options = options) 12 | if (interactive() || debug) print(getwd()) 13 | expect_true(file.exists("run1.mod")) 14 | system("execute run1.mod", intern = FALSE, ignore.stdout = TRUE, ignore.stderr = TRUE) 15 | if (interactive() && file.exists("run1.lst")) system("cat run1.lst") 16 | expect_true(file.exists("run1.lst")) 17 | } 18 | 19 | library(assemblerr) 20 | 21 | test_that("simple pred model", { 22 | m <- model() + 23 | prm_log_normal("v") + 24 | prm_log_normal("cl") + 25 | obs_additive(conc~amt/v*exp(-cl/v*time)) 26 | 27 | test_nm_model_execution(m) 28 | }) 29 | 30 | 31 | test_that("1cmp linear, advan", { 32 | m <- pk_model() + 33 | pk_distribution_1cmp() + 34 | pk_elimination_linear() + 35 | obs_additive(conc~C["central"]) 36 | 37 | test_nm_model_execution(m, 38 | assemblerr_options(ode.use_special_advans = TRUE)) 39 | }) 40 | 41 | test_that("1cmp linear, ode", { 42 | m <- pk_model() + 43 | pk_distribution_1cmp() + 44 | pk_elimination_linear() + 45 | obs_additive(conc~C["central"]) 46 | 47 | test_nm_model_execution(m, 48 | assemblerr_options(ode.use_special_advans = FALSE, 49 | ode.use_general_linear_advans = FALSE)) 50 | }) 51 | 52 | test_that("2cmp linear, fo absorption", { 53 | pkm <- pk_model() + 54 | pk_absorption_fo() + 55 | pk_distribution_2cmp() + 56 | pk_elimination_linear() + 57 | obs_additive(conc~C["central"]) 58 | 59 | test_nm_model_execution(pkm, assemblerr_options(ode.use_special_advans = TRUE)) 60 | }) 61 | -------------------------------------------------------------------------------- /tests/testthat/setup.R: -------------------------------------------------------------------------------- 1 | # ensure consisten output on CI system 2 | app <- cli::start_app(theme = list( 3 | ".alert-warning" = list(before = "WARNING! "), 4 | ".alert-success" = list(before = "SUCCESS! ") 5 | ), .auto_close = FALSE) 6 | 7 | 8 | withr::defer(cli::stop_app(app), teardown_env()) 9 | -------------------------------------------------------------------------------- /tests/testthat/test-facet.R: -------------------------------------------------------------------------------- 1 | context("facet manipulation") 2 | 3 | test_that("facet creation and addition of entries", { 4 | f <- Facet() 5 | e <- FacetEntry() 6 | expect_s4_class(f, "Facet") 7 | expect_s4_class(e, "FacetEntry") 8 | f <- add_entry(f, e) 9 | expect_equal(f@entries[[1]], e) 10 | }) 11 | 12 | test_that("named facet creation and addition of entries", { 13 | f <- NamedFacet() 14 | e <- NamedFacetEntry(name = "test") 15 | expect_s4_class(f, "NamedFacet") 16 | expect_s4_class(e, "NamedFacetEntry") 17 | f <- add_entry(f, e) 18 | expect_equal(f@entries[["test"]], e) 19 | }) 20 | 21 | -------------------------------------------------------------------------------- /tests/testthat/test-global-error-checking.R: -------------------------------------------------------------------------------- 1 | 2 | test_that("parameters", { 3 | m <- model() 4 | m2 <- m + prm_log_normal("test") 5 | expect_matching_issue(check(m), "No parameters") 6 | expect_no_matching_issue(check(m2), "No parameters") 7 | }) 8 | 9 | test_that("observation", { 10 | m <- model() 11 | m2 <- m + obs_additive(~test) 12 | expect_matching_issue(check(m), "No observation") 13 | expect_no_matching_issue(check(m2), "No observation") 14 | }) 15 | 16 | test_that("missing variables in algebraics", { 17 | m <- model() + 18 | algebraic(auc~dose/cl) 19 | m2 <- m + 20 | prm_log_normal("cl") + 21 | input_variable("dose") 22 | expect_matching_issue(check(m), "Undefined variables.*algebraics") 23 | expect_no_matching_issue(check(m2), "Undefined variables.*algebraics") 24 | }) 25 | 26 | test_that("missing variables in observation", { 27 | m <- model() + 28 | obs_additive(~dose/cl) 29 | m2 <- m + 30 | prm_log_normal("cl") + 31 | input_variable("dose") 32 | m3 <- model() + 33 | obs_additive(~C["central"]) 34 | m4 <- m3 + 35 | compartment("central") 36 | expect_matching_issue(check(m), "Undefined variables.*observation") 37 | expect_no_matching_issue(check(m2), "Undefined variables.*observation") 38 | expect_matching_issue(check(m3), "Undefined variable.*observation") 39 | expect_no_matching_issue(check(m4), "Undefined variable.*observation") 40 | 41 | }) 42 | 43 | test_that("missing compartment names in flow definition", { 44 | m <- model() + 45 | flow(~ka, from = "test") 46 | expect_matching_issue(check(m), "Undefined compartment name 'test' in flow definition") 47 | }) 48 | 49 | 50 | 51 | test_that("missing variables in flow definition", { 52 | m <- model() + 53 | flow(~ka, from = "test") 54 | expect_matching_issue(check(m), "Undefined variable.*flows") 55 | }) 56 | 57 | 58 | test_that("missing volume variables in compartment", { 59 | m <- model() + 60 | compartment("central", ~v) 61 | expect_matching_issue(check(m), "Undefined variable.*compartment") 62 | }) 63 | 64 | test_that("adding of missing variables", { 65 | m <- model() + 66 | prm_log_normal("v") + 67 | prm_log_normal("cl") + 68 | algebraic(d~dose) + 69 | obs_additive(conc~d/v*exp(-cl/v*time)) 70 | expect_warning( 71 | code <- render(m) 72 | ) 73 | expect_match(code, "\\$INPUT DOSE TIME") 74 | expect_silent( 75 | code <- render(m, options = assemblerr_options(issues.missing_variables = "fix")) 76 | ) 77 | expect_match(code, "\\$INPUT DOSE TIME") 78 | expect_error( 79 | code <- render(m, options = assemblerr_options(issues.missing_variables = "fail")) 80 | ) 81 | expect_silent( 82 | code <- render(m, options = assemblerr_options(issues.missing_variables = "ignore")) 83 | ) 84 | expect_match(code, "\\$INPUT ((?!DOSE).)*", perl = TRUE) 85 | 86 | }) 87 | -------------------------------------------------------------------------------- /tests/testthat/test-issues.R: -------------------------------------------------------------------------------- 1 | 2 | test_that("combining of issues", { 3 | expect_equal(c(IssueList(), Issue("test"), CriticalIssue("test2")), IssueList(Issue("test"), CriticalIssue("test2"))) 4 | }) 5 | 6 | 7 | test_that("printing of issues", { 8 | local_edition(3) 9 | local_reproducible_output() 10 | issues <- IssueList(Issue("test"), CriticalIssue("test2")) 11 | expect_snapshot(print(issues)) 12 | }) 13 | -------------------------------------------------------------------------------- /tests/testthat/test-local-error-checking.R: -------------------------------------------------------------------------------- 1 | 2 | # compartment ------------------------------------------------------------- 3 | 4 | 5 | test_that("compartment", { 6 | expect_error(compartment()) 7 | expect_error(compartment(1)) 8 | expect_error(compartment("test cmp")) 9 | expect_silent(compartment("test", 1)) 10 | expect_silent(compartment("test", ~vc)) 11 | }) 12 | 13 | 14 | # flow -------------------------------------------------------------------- 15 | 16 | 17 | test_that("flow", { 18 | expect_error(flow(~ka)) 19 | expect_error(flow(~ka*A, to = "depot")) 20 | expect_error(flow(~ka*C, to = "depot")) 21 | expect_silent(flow(~ka*C, from = "depot")) 22 | expect_silent(flow(~ka, to = "central")) 23 | expect_warning(flow(~ka*c, from = "depot")) 24 | }) 25 | 26 | 27 | 28 | # parameter --------------------------------------------------------------- 29 | test_that("parameter",{ 30 | prm_funs <- lsf.str("package:assemblerr", pattern = "^prm_") 31 | 32 | purrr::walk(prm_funs, ~expect_error(purrr::invoke(.x))) 33 | purrr::walk(prm_funs, ~expect_error(purrr::invoke(.x, name = 1))) 34 | purrr::walk(prm_funs, ~expect_error(purrr::invoke(.x, name = "_test"))) 35 | purrr::walk(prm_funs, ~expect_error(purrr::invoke(.x, name = "1a"))) 36 | purrr::walk(prm_funs, ~expect_silent(purrr::invoke(.x, name = "test123"))) 37 | 38 | }) 39 | 40 | # observation ------------------------------------------------------------- 41 | 42 | test_that("observation",{ 43 | obs_funs <- lsf.str("package:assemblerr", pattern = "^obs_") 44 | 45 | # declaration 46 | purrr::walk(obs_funs, ~expect_error(purrr::invoke(.x, prediction = "a+a"))) 47 | purrr::walk(obs_funs, ~expect_error(purrr::invoke(.x, prediction = quote(a+a)))) 48 | purrr::walk(obs_funs, ~expect_silent(purrr::invoke(.x, prediction = "test123"))) 49 | purrr::walk(obs_funs, ~expect_silent(purrr::invoke(.x, prediction = ~test))) 50 | purrr::walk(obs_funs, ~expect_silent(purrr::invoke(.x, prediction = ~C["central"]))) 51 | 52 | # name 53 | purrr::walk(obs_funs, ~expect_error(purrr::invoke(.x, prediction = ~test, name = "_test"))) 54 | purrr::walk(obs_funs, ~expect_silent(purrr::invoke(.x, prediction = ~test, name = "conc"))) 55 | 56 | }) 57 | -------------------------------------------------------------------------------- /tests/testthat/test-model.R: -------------------------------------------------------------------------------- 1 | local_edition(3) 2 | local_reproducible_output() 3 | 4 | 5 | 6 | test_that("check empty model",{ 7 | expect_snapshot(check(model())) 8 | }) 9 | 10 | test_that("check simple model",{ 11 | expect_snapshot(check(simple_model())) 12 | }) 13 | 14 | 15 | test_that("required crtl records", { 16 | simple_model() %>% 17 | render() %>% 18 | expect_contains("$PROBLEM") %>% 19 | expect_contains("$INPUT") %>% 20 | expect_contains("$PRED") 21 | }) 22 | 23 | test_that("prm normal distribution", { 24 | simple_model(prm = prm_normal("k", mean = 2, var = 0.5)) %>% 25 | render(options = assemblerr_options(prm.use_mu_referencing = TRUE)) %>% 26 | expect_contains("MU_1 = THETA(1)") %>% 27 | expect_contains("K = MU_1 + ETA(1)") %>% 28 | expect_contains("$OMEGA 0.5") %>% 29 | expect_match("\\$THETA .*2") 30 | }) 31 | 32 | test_that("prm log-normal distribution", { 33 | simple_model(prm = prm_log_normal("k", median = 2, var_log = 0.09)) %>% 34 | render(options = assemblerr_options(prm.use_mu_referencing = TRUE)) %>% 35 | expect_contains("MU_1 = LOG(THETA(1))") %>% 36 | expect_contains("K = EXP(MU_1 + ETA(1))") %>% 37 | expect_contains("$OMEGA 0.09") %>% 38 | expect_match("\\$THETA .*2") 39 | }) 40 | 41 | test_that("prm novar distribution", { 42 | simple_model(prm = prm_no_var("k", value = 5)) %>% 43 | render(options = assemblerr_options(prm.use_mu_referencing = TRUE)) %>% 44 | expect_contains("K = THETA(1)") %>% 45 | expect_match("\\$THETA .*5") 46 | }) 47 | 48 | test_that("prm logit distribution", { 49 | simple_model(prm = prm_logit_normal("k", mean_logit = 1, var_logit = 2)) %>% 50 | render(options = assemblerr_options(prm.use_mu_referencing = TRUE)) %>% 51 | expect_contains("MU_1 = LOG(THETA(1))/(1 - LOG(THETA(1)))") %>% 52 | expect_contains("LOGIT_K = MU_1 + ETA(1)") %>% 53 | expect_contains("K = EXP(LOGIT_K)/(1 + EXP(LOGIT_K))") %>% 54 | expect_match("\\$THETA .*1") %>% 55 | expect_contains("$OMEGA 2") 56 | }) 57 | 58 | 59 | test_that("obs additive", { 60 | simple_model(obs = obs_additive(c ~ conc, var_add = 2)) %>% 61 | render() %>% 62 | expect_contains("C = CONC") %>% 63 | expect_contains("Y = C + EPS(1)") %>% 64 | expect_contains("$SIGMA 2") 65 | }) 66 | 67 | test_that("obs proportional", { 68 | simple_model(obs = obs_proportional(c ~ conc, var_prop = 0.2)) %>% 69 | render() %>% 70 | expect_contains("C = CONC") %>% 71 | expect_contains("Y = C + C * EPS(1)") %>% 72 | expect_contains("$SIGMA 0.2") 73 | }) 74 | 75 | test_that("obs combined", { 76 | simple_model(obs = obs_combined(c ~ conc, var_prop = 0.2, var_add = 2)) %>% 77 | render() %>% 78 | expect_contains("C = CONC") %>% 79 | expect_contains("Y = C + EPS(1) + C * EPS(2)") %>% 80 | expect_contains("$SIGMA 0.2") %>% 81 | expect_contains("$SIGMA 2") 82 | 83 | }) 84 | 85 | test_that("obs without lhs", { 86 | simple_model(obs = obs_additive(~ conc)) %>% 87 | render() %>% 88 | expect_does_not_contain("C = CONC") %>% 89 | expect_contains("Y = CONC + EPS(1)") %>% 90 | expect_contains("$SIGMA") 91 | }) 92 | 93 | test_that("adding variables from a dataset", { 94 | m <- simple_model(vars = NULL) 95 | local_create_nonmem_test_directory() 96 | df <- data.frame(ID = 1, TIME = 1, DV = 1, DOSE = 1, C0 = 1) 97 | write.csv(df, "data.csv", quote = FALSE, row.names = FALSE) 98 | m <- m + 99 | dataset(path = "data.csv") 100 | render(m) %>% 101 | expect_contains("$INPUT ID TIME DV DOSE") %>% 102 | expect_contains("$DATA data.csv IGNORE=@") 103 | }) 104 | 105 | test_that("adding variables from a dataset with duplicated columns", { 106 | m <- simple_model(vars = NULL) 107 | local_create_nonmem_test_directory() 108 | df <- data.frame(ID = 1, TIME = 1, DV = 1, DOSE = 1, DOSE = 2, C0 = 1, check.names = FALSE) 109 | write.csv(df, "data.csv", quote = FALSE, row.names = FALSE) 110 | expect_warning( 111 | m <- m + 112 | dataset(path = "data.csv") 113 | ) 114 | render(m) %>% 115 | expect_contains("$INPUT ID TIME DV DOSE DOSE_1") %>% 116 | expect_contains("$DATA data.csv IGNORE=@") 117 | }) 118 | 119 | 120 | 121 | test_that("adding incompatible building block", { 122 | m <- simple_model() 123 | 124 | expect_warning( 125 | m + pk_absorption_fo() 126 | ) 127 | }) 128 | -------------------------------------------------------------------------------- /tests/testthat/test-nodes.R: -------------------------------------------------------------------------------- 1 | test_that("adding NamedNodes to NodeList", { 2 | nl <- NodeList() + NamedNode(name = "test") 3 | expect_is(nl, "NodeList") 4 | expect_length(nl, 1) 5 | expect_equal(nl[[1]]@name, "test") 6 | }) 7 | 8 | test_that("adding NamedNodes to NamedNodeList", { 9 | nl <- NamedNodeList() + NamedNode(name = "test") 10 | expect_is(nl, "NodeList") 11 | expect_length(nl, 1) 12 | expect_equal(nl[[1]]@name, "test") 13 | expect_equal(nl[["test"]]@name, "test") 14 | }) 15 | 16 | test_that("combining NodeLists", { 17 | nl0 <- NodeList() + NodeList() 18 | expect_is(nl0, "NodeList") 19 | expect_length(nl0, 0) 20 | nl2 <- NodeList() + NamedNode(name = "test") + {NodeList() + NamedNode(name = "test2")} 21 | expect_is(nl2, "NodeList") 22 | expect_length(nl2, 2) 23 | expect_equal(nl2[[1]]@name, "test") 24 | expect_equal(nl2[[2]]@name, "test2") 25 | }) 26 | 27 | 28 | test_that("combining NamedNodeLists", { 29 | nl0 <- NamedNodeList() + NamedNodeList() 30 | expect_is(nl0, "NamedNodeList") 31 | expect_length(nl0, 0) 32 | nl2 <- NamedNodeList() + NamedNode(name = "test") + {NamedNodeList() + NamedNode(name = "test2")} 33 | expect_is(nl2, "NamedNodeList") 34 | expect_length(nl2, 2) 35 | expect_equal(nl2[[1]]@name, "test") 36 | expect_equal(nl2[[2]]@name, "test2") 37 | expect_equal(nl2[["test"]]@name, "test") 38 | expect_equal(nl2[["test2"]]@name, "test2") 39 | }) 40 | -------------------------------------------------------------------------------- /tests/testthat/test-ode-model.R: -------------------------------------------------------------------------------- 1 | test_that("2 cmp, fo absorption as ADVAN 4, TRANS4", { 2 | m <- model() + 3 | prm_log_normal("KA") + 4 | prm_log_normal("CL") + 5 | prm_log_normal("V2") + 6 | prm_log_normal("Q") + 7 | prm_log_normal("V3") + 8 | compartment("dose") + 9 | compartment("central", volume = ~V2) + 10 | compartment("peripheral", volume = ~V3) + 11 | flow(from = "dose", to = "central", definition = ~KA*A ) + 12 | flow(from = "central", definition = ~CL/V2*A) + 13 | flow(from = "central", to = "peripheral", definition = ~Q/V2*A) + 14 | flow(from = "peripheral", to = "central", definition = ~Q/V3*A) + 15 | obs_additive(conc~C["central"]) 16 | 17 | render(m) %>% 18 | expect_contains("$SUBROUTINES ADVAN4 TRANS4") %>% 19 | expect_contains("CONC = A(2)/V2") %>% 20 | expect_contains("Y = CONC + EPS(1)") 21 | }) 22 | 23 | 24 | test_that("2 cmp, fo absorption, with parentheses as ADVAN 4, TRANS1", { 25 | m <- model() + 26 | prm_log_normal("KA") + 27 | prm_log_normal("CL") + 28 | prm_log_normal("V2") + 29 | prm_log_normal("Q") + 30 | prm_log_normal("V3") + 31 | compartment("dose") + 32 | compartment("central", volume = ~V2) + 33 | compartment("peripheral", volume = ~V3) + 34 | flow(from = "dose", to = "central", definition = ~KA*A )+ 35 | flow(from = "central", definition = ~(CL/V2)*A) + 36 | flow(from = "central", to = "peripheral", definition = ~(Q/V2)*A) + 37 | flow(from = "peripheral", to = "central", definition = ~(Q/V3)*A) + 38 | obs_additive(conc~C["central"]) 39 | 40 | expect_warning(render(m)) %>% 41 | expect_contains("$SUBROUTINES ADVAN4 TRANS1") %>% 42 | expect_contains("K12 = (Q/V2)") %>% 43 | expect_contains("K = (CL/V2)") %>% 44 | expect_contains("K21 = (Q/V3)") %>% 45 | expect_contains("CONC = A(2)/V2") %>% 46 | expect_contains("Y = CONC + EPS(1)") 47 | }) 48 | 49 | test_that("2 cmp, fo absorption, micro constants as ADVAN 4, TRANS1", { 50 | m <- model() + 51 | prm_log_normal("KA") + 52 | prm_log_normal("K") + 53 | prm_log_normal("K23") + 54 | prm_log_normal("K32") + 55 | prm_log_normal("V") + 56 | compartment("dose") + 57 | compartment("central", volume = ~V) + 58 | compartment("peripheral") + 59 | flow(from = "dose", to = "central", definition = ~KA*A ) + 60 | flow(from = "central", definition = ~K*A) + 61 | flow(from = "central", to = "peripheral", definition = ~K23*A) + 62 | flow(from = "peripheral", to = "central", definition = ~K32*A) + 63 | obs_additive(conc~C["central"]) 64 | 65 | expect_warning(render(m)) %>% 66 | expect_contains("$SUBROUTINES ADVAN4 TRANS1") %>% 67 | expect_contains("CONC = A(2)/V") %>% 68 | expect_contains("Y = CONC + EPS(1)") 69 | }) 70 | -------------------------------------------------------------------------------- /tests/testthat/test-statement.R: -------------------------------------------------------------------------------- 1 | context("test-statement") 2 | 3 | test_that("creation", { 4 | s <- statement(quote(cl <- theta[1]*exp(eta[1])), 5 | quote(v <- theta[2])) 6 | expect_s3_class(s, "assemblerr_statement") 7 | expect_length(s, 2) 8 | }) 9 | 10 | test_that("creation from character", { 11 | expect_equal( 12 | statement("cl <- theta"), 13 | statement(quote(cl <- theta)) 14 | ) 15 | index <- 5 16 | expect_equal( 17 | statement("cl <- theta[{index}]"), 18 | statement(quote(cl <- theta[5])) 19 | ) 20 | }) 21 | 22 | test_that("creation with quoting works", { 23 | a <- 10 24 | s <- statement(bquote(cl <- theta[.(a)]*exp(eta[.(a)]))) 25 | expect_equal(s, statement(quote(cl <- theta[10]*exp(eta[10])))) 26 | }) 27 | 28 | 29 | test_that("conversion from declaration",{ 30 | d <- declaration(cl~theta[1]*exp(eta[1]), v ~ theta[2], ~exp(eta[1])) 31 | s <- as_statement(d) 32 | expect_equal(s[1], statement(quote(cl <- theta[1]*exp(eta[1])))) 33 | expect_equal(s[2], statement(quote(v <- theta[2]))) 34 | expect_equal(s[3], statement(quote(exp(eta[1])))) 35 | }) 36 | 37 | test_that("code rendering", { 38 | s <- statement( 39 | quote(cl <- theta[1]*exp(eta[1])), 40 | quote(v <- theta[2]) 41 | ) 42 | expect_equal(render_component(s), 43 | "CL = THETA(1) * EXP(ETA(1))\nV = THETA(2)") 44 | 45 | }) 46 | -------------------------------------------------------------------------------- /tests/testthat/test-tasks.R: -------------------------------------------------------------------------------- 1 | test_that("estimation task", { 2 | m <- simple_model() 3 | render(m, tasks = tsk_estimation(algorithm = "foce")) %>% 4 | expect_contains("$ESTIMATION METHOD=COND") %>% 5 | expect_does_not_contain("INTERACTION") 6 | 7 | render(m, tasks = tsk_estimation(algorithm = "foce", se = TRUE)) %>% 8 | expect_contains("$ESTIMATION METHOD=COND") %>% 9 | expect_contains("$COVARIANCE") 10 | 11 | m2 <- simple_model(obs = obs_proportional(~conc)) 12 | render(m2, tasks = tsk_estimation(algorithm = "foce")) %>% 13 | expect_match("\\$ESTIMATION METHOD=COND INTERACTION") 14 | }) 15 | 16 | test_that("estimation task with additional options", { 17 | m <- simple_model() 18 | render(m, tasks = tsk_estimation(algorithm = "foce", target_options = list(test = 1))) %>% 19 | expect_match("\\$ESTIMATION .* TEST=1") 20 | 21 | render(m, tasks = tsk_estimation(algorithm = "saem", target_options = list(auto = FALSE))) %>% 22 | expect_match("\\$ESTIMATION METHOD=SAEM AUTO=0") 23 | 24 | render(m, tasks = tsk_estimation(algorithm = "saem", target_options = list(AUTO = FALSE))) %>% 25 | expect_match("\\$ESTIMATION METHOD=SAEM AUTO=0") 26 | }) 27 | 28 | test_that("output task parameters", { 29 | m <- simple_model() 30 | render(m, tasks = tsk_output("sdtab", variables = vars_prms())) %>% 31 | expect_match("\\$TABLE.*K.*FILE=sdtab") 32 | }) 33 | 34 | test_that("output task standard variables", { 35 | m <- simple_model() 36 | render(m, tasks = tsk_output("sdtab", variables = vars_nm_std())) %>% 37 | expect_match("\\$TABLE.*DV") %>% 38 | expect_match("\\$TABLE.*PRED") %>% 39 | expect_match("\\$TABLE.*RES") %>% 40 | expect_match("\\$TABLE.*WRES") %>% 41 | expect_match("\\$TABLE.*IPREDI") %>% 42 | expect_match("\\$TABLE.*IWRESI") 43 | }) 44 | 45 | test_that("output task eta variables", { 46 | m <- simple_model() 47 | render(m, tasks = tsk_output("sdtab", variables = vars_eta())) %>% 48 | expect_match("\\$TABLE.*ETA\\(1\\)") 49 | }) 50 | 51 | test_that("output task data variables", { 52 | m <- simple_model() 53 | render(m, tasks = tsk_output("sdtab", variables = vars_data())) %>% 54 | expect_match("\\$TABLE.*TIME") %>% 55 | expect_match("\\$TABLE.*C0") 56 | }) 57 | 58 | test_that("xpose4 output task ", { 59 | m <- simple_model() 60 | render(m, tasks = tsk_output_xpose4()) %>% 61 | expect_match("\\$TABLE.*ID.*FILE=sdtab") %>% 62 | expect_match("\\$TABLE.*TIME.*FILE=sdtab") %>% 63 | expect_match("\\$TABLE.*DV.*FILE=sdtab") %>% 64 | expect_match("\\$TABLE.*PRED.*FILE=sdtab") %>% 65 | expect_match("\\$TABLE.*RES.*FILE=sdtab") %>% 66 | expect_match("\\$TABLE.*WRES.*FILE=sdtab") %>% 67 | expect_match("\\$TABLE.*IPREDI.*FILE=sdtab") %>% 68 | expect_match("\\$TABLE.*IWRESI.*FILE=sdtab") %>% 69 | expect_match("\\$TABLE.*K.*FILE=patab") %>% 70 | expect_match("\\$TABLE.*ETA\\(1\\).*FILE=patab") 71 | }) 72 | -------------------------------------------------------------------------------- /tests/testthat/test-test-helpers.R: -------------------------------------------------------------------------------- 1 | test_that("creation of dummy data", { 2 | dir <- local_create_nonmem_test_directory() 3 | m <- model() + 4 | prm_log_normal("v") + 5 | prm_log_normal("cl") + 6 | obs_additive(conc~amt/v*exp(-cl/v*time)) 7 | create_dummy_data(m, path = "data.csv") 8 | expect_true(file.exists(file.path(dir, "data.csv"))) 9 | }) 10 | 11 | test_that("does_not_contain expectation", { 12 | expect_success(expect_does_not_contain(c("test", "test2"), "test3")) 13 | expect_failure(expect_does_not_contain(c("test", "test2"), "test2")) 14 | }) 15 | 16 | test_that("expect_matching_issue helper", { 17 | issues <- IssueList( 18 | Issue("test issue") 19 | ) 20 | expect_success( 21 | expect_matching_issue(issues, "test") 22 | ) 23 | expect_failure( 24 | expect_matching_issue(issues, "missing") 25 | ) 26 | }) 27 | 28 | test_that("expect_no_matching_issue helper", { 29 | issues <- IssueList( 30 | Issue("test issue") 31 | ) 32 | expect_success( 33 | expect_no_matching_issue(issues, "missing") 34 | ) 35 | expect_failure( 36 | expect_no_matching_issue(issues, "test") 37 | ) 38 | }) 39 | 40 | 41 | 42 | test_that("simple model helper", { 43 | m <- simple_model(prm = prm_normal("test")) 44 | expect_s4_class(m, "Model") 45 | expect_s4_class(m@facets$ParameterFacet@entries[[1]], "PrmNormal") 46 | }) 47 | -------------------------------------------------------------------------------- /tests/testthat/test-util.R: -------------------------------------------------------------------------------- 1 | test_that("facet class name to labels", { 2 | expect_equal(facet_names_to_labels(c("ParameterFacet","InputVariableFacet")), c("parameter", "input variable")) 3 | }) 4 | 5 | test_that("string interpolation", { 6 | x <- "test" 7 | expect_equal(interp("this is a {x}"), "this is a test") 8 | entries <- 1:3 9 | expect_equal(interp("{length(entries)} {?entry/entries}: {entries}"), "3 entries: 1, 2, and 3") 10 | }) 11 | -------------------------------------------------------------------------------- /tests/testthat/test-variable-renaming.R: -------------------------------------------------------------------------------- 1 | test_that("renaming in analytic model", { 2 | simple_model() %>% 3 | rename_variables(c(k = "k1")) %>% 4 | render() %>% 5 | expect_contains("K1 = THETA(1) * EXP(ETA(1))") %>% 6 | expect_contains("CONC = C0 * EXP(-K1 * TIME)") 7 | 8 | simple_model(obs = obs_additive(c~conc)) %>% 9 | rename_variables(c(conc = "conc2")) %>% 10 | render() %>% 11 | expect_contains("C = CONC2") 12 | }) 13 | 14 | 15 | test_that("renaming in ode model", { 16 | simple_ode_model() %>% 17 | rename_variables(c(cl = "cl2")) %>% 18 | render() %>% 19 | expect_contains("CL2 = ") %>% 20 | expect_contains("CL = CL2") 21 | }) 22 | 23 | 24 | test_that("renaming in PK model", { 25 | simple_pk_model() %>% 26 | rename_variables(c(cl = "cl2")) %>% 27 | render() %>% 28 | expect_contains("CL2 = ") %>% 29 | expect_contains("CL = CL2") 30 | }) 31 | 32 | test_that("model rendering", { 33 | m <- simple_model() + 34 | prm_normal("K") 35 | 36 | expect_warning(render(m), "Variables renamed") %>% 37 | expect_contains("K1 = ") 38 | }) 39 | 40 | test_that("pk_model rendering", { 41 | m <- simple_pk_model() + 42 | prm_normal("Mat") 43 | 44 | expect_warning(render(m), "Variables renamed") %>% 45 | expect_contains("MAT1 = ") 46 | }) 47 | -------------------------------------------------------------------------------- /vignettes/concepts.bak: -------------------------------------------------------------------------------- 1 | --- 2 | title: "Package Concepts" 3 | author: "Sebastian Ueckert" 4 | date: "`r Sys.Date()`" 5 | output: rmarkdown::html_vignette 6 | vignette: > 7 | %\VignetteIndexEntry{Vignette Title} 8 | %\VignetteEngine{knitr::rmarkdown} 9 | %\VignetteEncoding{UTF-8} 10 | --- 11 | 12 | ```{r setup, include = FALSE} 13 | knitr::opts_chunk$set( 14 | collapse = TRUE, 15 | comment = "#>" 16 | ) 17 | ``` 18 | 19 | The `assemblerr` package allows to quickly describe complex pharmacometric models using a set of elementary building blocks and then to generate NONMEM code for these models. In `assemblerr`, each of these two steps use a different representation of the model. The model object in step 1 is only concerned with the pharmacometric substance of the model and the model in step two is mainly concerned with the 20 | 21 | is implem distinguishes between two types of models **decl**, a model consists of a set of **facets** 22 | 23 | __Model__: A parameterized representation of a data generating process 24 | 25 | __Facet:__ An aspect of a model that can be changed 26 | 27 | __Fragment__: One or more facets together with their properties 28 | 29 | - Use R syntax but software-specific semantics 30 | 31 | # Conversion diagram 32 | 33 | ```{r, echo=FALSE, fig.height=5, fig.width=7} 34 | DiagrammeR::mermaid(" 35 | graph TD 36 | subgraph domain specific 37 | A[pk_model] 38 | B[pbpk_model] 39 | C[pd_model] 40 | end 41 | A --> D[model] 42 | B --> D 43 | C --> D 44 | subgraph software specifc 45 | E[model_nm] 46 | F[model_mlx] 47 | G[model_poped] 48 | end 49 | D --> E 50 | D --> F 51 | D --> G 52 | ") 53 | ``` 54 | 55 | 56 | 57 | __Declaration__: The mathematical definition of a variable as a function of other variables 58 | 59 | __Statement__: The expression of an action to be carried out 60 | -------------------------------------------------------------------------------- /vignettes/experimental.bak: -------------------------------------------------------------------------------- 1 | --- 2 | title: "Experimental" 3 | author: "Sebastian Ueckert" 4 | date: "`r Sys.Date()`" 5 | output: rmarkdown::html_vignette 6 | vignette: > 7 | %\VignetteIndexEntry{Experimental} 8 | %\VignetteEngine{knitr::rmarkdown} 9 | %\VignetteEncoding{UTF-8} 10 | --- 11 | 12 | ```{r setup, include = FALSE} 13 | knitr::opts_chunk$set( 14 | collapse = TRUE, 15 | comment = "#>" 16 | ) 17 | ``` 18 | 19 | This vignette documents some of the more experimental features of the package. 20 | 21 | # PRED models 22 | 23 | assemblerr autmoatically generates a PRED model when no differential equations are present. 24 | 25 | 26 | ```{r} 27 | library(assemblerr, warn.conflicts = F) 28 | 29 | # construct one-compartment 1st order elimination model 30 | m <- model()+ 31 | algebraic(effect~emax*dose/(ed50+dose))+ 32 | prm_log_normal("EMAX")+ 33 | prm_log_normal("ED50")+ 34 | obs_additive(eff~effect, "effect")+ 35 | obs_additive(~emax, "emax") 36 | 37 | # convert to a NONMEM model and generate NMTran code 38 | as_nm_model(m) %>% 39 | render %>% 40 | cat() 41 | ``` 42 | 43 | # Automatic ordering of variables 44 | 45 | assemblerrr uses a declarative philosophy to specify models, in consequence the order of statements does not matter. When the NONMEM model is generated, assemblerr will determine the appropriate order of instructions and assign each instruction to the suitable block (PK, DES, ERROR) . 46 | 47 | ```{r} 48 | 49 | 50 | m <- model()+ 51 | compartment("central", volume = ~vc) + 52 | flow(from = "central", definition = ~cl*C) + 53 | flow(to = "central", definition = ~kin) + 54 | prm_log_normal("cl") + 55 | prm_log_normal("vc") + 56 | algebraic(k~cl/v)+ 57 | algebraic(conc~A["central"])+ 58 | algebraic(kin~k*A["central"])+ 59 | obs_additive(~conc, "conc") 60 | 61 | 62 | # convert to a NONMEM model and generate NMTran code 63 | as_nm_model(m) %>% 64 | render %>% 65 | cat() 66 | 67 | ``` 68 | 69 | # Multiple observation models 70 | 71 | assemblerr supports multiple observation models per model 72 | 73 | ```{r, eval=F} 74 | m <- model()+ 75 | compartment("central", volume = ~vc) + 76 | flow(from = "central", definition = ~cl*C) + 77 | prm_log_normal("cl") + 78 | prm_log_normal("vc") + 79 | prm_normal("emax")+ 80 | prm_novar("ed50")+ 81 | algebraic(conc~C["central"])+ 82 | obs_additive(~conc, name = "PK") + 83 | obs_additive(~emax*conc/(conc+ed50), name = "PD") 84 | 85 | m %>% 86 | as_model_nm() %>% 87 | render() %>% 88 | cat() 89 | 90 | ``` 91 | 92 | # Model visualization 93 | 94 | assemblerr can create a simple visualization of the model 95 | 96 | ```{r, fig.height=5, fig.width=7} 97 | pkm <- pk_model()+ 98 | pk_distribution_3cmp()+ 99 | pk_elemination_linear()+ 100 | pk_absorption_rate_fo() 101 | 102 | pkm %>% 103 | as_model() %>% 104 | visualize() 105 | 106 | ``` 107 | 108 | # Conversion diagram 109 | 110 | ```{r, echo=FALSE, fig.height=5, fig.width=7} 111 | DiagrammeR::mermaid(" 112 | graph TD 113 | subgraph domain specific 114 | A[pk_model] 115 | B[pbpk_model] 116 | C[pd_model] 117 | end 118 | A --> D[model] 119 | B --> D 120 | C --> D 121 | subgraph software specifc 122 | E[model_nm] 123 | F[model_mlx] 124 | G[model_poped] 125 | end 126 | D --> E 127 | D --> F 128 | D --> G 129 | ") 130 | ``` 131 | 132 | # Conditional declarations 133 | 134 | assemblerr supports conditional declarations through the function `cases`. Examples 135 | 136 | - Different typical values for males and females `cl~cases(sex, 0 ~ theta[1], 1 ~ theta[2])*exp(eta[1])` 137 | - Probabilities for binary response `p~cases(y, 0 ~ p0, 1 ~ 1 - p0)` 138 | - Censoring due to quantification limits `cases(conc, conc > 1 ~ ipred, conc <= 1 ~ prob)` 139 | 140 | 141 | ```{r, eval=FALSE} 142 | as_declaration(cl~cases(sex, 0 ~ theta[1], 1 ~ theta[2])*exp(eta[1])) %>% 143 | render(render_opts_nm()) %>% 144 | cat() 145 | ``` 146 | 147 | # Binary observations 148 | 149 | ```{r, eval =FALSE} 150 | m <- model()+ 151 | prm_logit("pbase")+ 152 | obs_binary(~pbase, "effect") 153 | 154 | # convert to a NONMEM model and generate NMTran code 155 | as_nm_model(m) %>% 156 | render %>% 157 | cat() 158 | ``` 159 | 160 | # Support for PKPDsim 161 | 162 | ```{r, eval=FALSE} 163 | m <- model()+ 164 | compartment("central", volume = ~vc) + 165 | flow(from = "central", definition = ~cl*C) + 166 | prm_log_normal("cl") + 167 | prm_log_normal("vc") 168 | 169 | m_sim <- m %>% 170 | as_model_pkpd_sim() 171 | 172 | m_sim$odes 173 | 174 | ``` 175 | 176 | --------------------------------------------------------------------------------