diff --git a/.github/workflows/R-CMD-check.yml b/.github/workflows/R-CMD-check.yml index def073c..5516bf0 100644 --- a/.github/workflows/R-CMD-check.yml +++ b/.github/workflows/R-CMD-check.yml @@ -14,7 +14,7 @@ on: - "**.json" - "**.md" - "**.yml" - - "!**R-cmd-check.yml" + - "!**R-CMD-check.yml" - "**.R[dD]ata" - "**.Rpro*" pull_request: @@ -29,7 +29,7 @@ on: - "**.json" - "**.md" - "**.yml" - - "!**R-cmd-check.yml" + - "!**R-CMD-check.yml" - "**.R[dD]ata" - "**.Rpro*" @@ -61,96 +61,75 @@ jobs: GITHUB_PAT: ${{ secrets.GITHUB_TOKEN }} steps: - - uses: actions/checkout@v3 + - uses: actions/checkout@v4 with: submodules: true + + - name: Install system dependencies (Linux) + if: runner.os == 'Linux' + run: | + sudo apt-get update -y + sudo apt-get install -y libpoppler-glib-dev bwidget libavfilter-dev libtesseract-dev gdal-bin proj-bin libgdal-dev libproj-dev tesseract-ocr-eng libleptonica-dev tcl libgtk2.0-dev libgtk-3-dev + sudo pkg-config --libs poppler-glib + sudo pkg-config --cflags poppler-glib - uses: r-lib/actions/setup-r@v2 with: r-version: ${{ matrix.config.r }} - + - uses: r-lib/actions/setup-pandoc@v2 - - - name: Query dependencies - if: runner.os != 'macOS' - run: | - install.packages('remotes') - saveRDS( - remotes::dev_package_deps(dependencies = c("soft", - "Config/Needs/github-actions")), ".github/depends.Rds", version = 2) - writeLines(sprintf("R-%i.%i", getRversion()$major, getRversion()$minor), - ".github/R-version") - shell: Rscript {0} - - - name: Query dependencies (macOS) - if: runner.os == 'macOS' - run: | - install.packages('remotes') - saveRDS( - remotes::dev_package_deps(dependencies = c("soft", - "Config/Needs/coverage", "Config/Needs/github-actions")) - , ".github/depends.Rds", version = 2) - writeLines(sprintf("R-%i.%i", getRversion()$major, getRversion()$minor), - ".github/R-version") - shell: Rscript {0} - + - name: Cache R packages - if: runner.os != 'Windows' - uses: actions/cache@v3 + uses: actions/cache@v4 with: path: ${{ env.R_LIBS_USER }} key: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1-${{ hashFiles('.github/depends.Rds') }} restore-keys: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1- - - - name: Install system dependencies (Linux) - if: runner.os == 'Linux' - run: | - sudo apt-get update -y - sudo apt-get install -y libpoppler-glib-dev bwidget libavfilter-dev libtesseract-dev gdal-bin proj-bin libgdal-dev libproj-dev tesseract-ocr-eng libleptonica-dev tcl libgtk2.0-dev libgtk-3-dev - sudo pkg-config --libs poppler-glib - sudo pkg-config --cflags poppler-glib - while read -r cmd - do - eval sudo $cmd - done < <(Rscript -e 'writeLines(remotes::system_requirements("ubuntu", "20.04"))') - + - name: Install system dependencies (macOS) if: runner.os == 'macOS' run: | brew install libgit2 xquartz - - name: Install callr (Windows) + - name: Set up R dependencies (Windows) if: runner.os == 'Windows' - run: | - remotes::install_cran("callr") - shell: Rscript {0} - - - name: Install dependencies - run: | - remotes::install_deps(dependencies = c("soft", "Config/Needs/github-actions")) - shell: Rscript {0} - - - name: Install coverage dependencies - if: runner.os == 'macOS' - run: | - remotes::install_deps(dependencies = 'Config/Needs/coverage') - shell: Rscript {0} - - - name: Check - env: - _R_CHECK_CRAN_INCOMING_REMOTE_: false - run: rcmdcheck::rcmdcheck(args = c("--no-manual", "--as-cran"), error_on = "warning", check_dir = "check") - shell: Rscript {0} - - # - name: Upload check results - # if: failure() - # uses: actions/upload-artifact@main - # with: - # name: ${{ runner.os }}-r${{ matrix.config.r }}-results - # path: check + uses: r-lib/actions/setup-r-dependencies@v2 + with: + extra-packages: callr + needs: | + check + coverage + github-actions + + - name: Set up R dependencies (Non-Windows) + if: runner.os != 'Windows' + uses: r-lib/actions/setup-r-dependencies@v2 + with: + needs: | + check + github-actions + extra-packages: | + phangorn=?ignore-before-r=4.1.0 + + - name: Check package + uses: r-lib/actions/check-r-package@v2 - name: Test coverage - if: runner.os == 'macOS' + if: runner.os == 'Windows' run: | covr::codecov() shell: Rscript {0} + + - name: Notify on failure + if: failure() && github.event_name == 'schedule' + uses: actions/github-script@v7 + with: + github-token: ${{ secrets.GITHUB_TOKEN }} + script: | + github.rest.issues.createComment({ + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: 31, + body: 'Scheduled workflow has failed: https://github.com/${{ github.repository }}/actions/runs/${{ github.run_id }}' + }); + diff --git a/.github/workflows/RcppDeepState.yml b/.github/workflows/RcppDeepState.yml index e34a4be..bbac34e 100644 --- a/.github/workflows/RcppDeepState.yml +++ b/.github/workflows/RcppDeepState.yml @@ -32,7 +32,7 @@ jobs: GITHUB_PAT: ${{ secrets.GITHUB_TOKEN }} steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 with: submodules: true diff --git a/.github/workflows/codemeta.yml b/.github/workflows/codemeta.yml index 82ee53a..e1ae6e5 100644 --- a/.github/workflows/codemeta.yml +++ b/.github/workflows/codemeta.yml @@ -20,7 +20,7 @@ jobs: RSPM: ${{ matrix.config.rspm }} steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 - uses: r-lib/actions/setup-r@v2 with: @@ -37,7 +37,7 @@ jobs: shell: Rscript {0} - name: Cache R packages - uses: actions/cache@v2 + uses: actions/cache@v4 with: path: ${{ env.R_LIBS_USER }} key: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1-${{ hashFiles('.github/depends.Rds') }} diff --git a/.github/workflows/memcheck.yml b/.github/workflows/memcheck.yml index 2b961b6..657b0b3 100644 --- a/.github/workflows/memcheck.yml +++ b/.github/workflows/memcheck.yml @@ -42,7 +42,7 @@ jobs: GITHUB_PAT: ${{ secrets.GITHUB_TOKEN }} steps: - - uses: actions/checkout@v3 + - uses: actions/checkout@v4 with: submodules: true @@ -66,7 +66,7 @@ jobs: shell: Rscript {0} - name: Cache R packages - uses: actions/cache@v2 + uses: actions/cache@v4 with: path: ${{ env.R_LIBS_USER }} key: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1-${{ hashFiles('.github/depends.Rds') }} diff --git a/.github/workflows/pkgdown.yml b/.github/workflows/pkgdown.yml index 985eb5a..9e3ac54 100644 --- a/.github/workflows/pkgdown.yml +++ b/.github/workflows/pkgdown.yml @@ -22,7 +22,7 @@ jobs: R_COMPILE_AND_INSTALL_PACKAGES: 'never' steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 with: submodules: true @@ -38,7 +38,7 @@ jobs: shell: Rscript {0} - name: Cache R packages - uses: actions/cache@v2 + uses: actions/cache@v4 with: path: ${{ env.R_LIBS_USER }} key: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1-${{ hashFiles('.github/depends.Rds') }} diff --git a/.github/workflows/revdepcheck.yml b/.github/workflows/revdepcheck.yml index 37ab7c0..4538ad4 100644 --- a/.github/workflows/revdepcheck.yml +++ b/.github/workflows/revdepcheck.yml @@ -59,7 +59,7 @@ jobs: GITHUB_PAT: ${{ secrets.GITHUB_TOKEN }} steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 - uses: r-lib/actions/setup-r@v2 with: @@ -76,7 +76,7 @@ jobs: shell: Rscript {0} - name: Cache R packages - uses: actions/cache@v2 + uses: actions/cache@v4 with: path: ${{ env.R_LIBS_USER }} key: ${{ runner.os }}-${{ hashFiles('.github/R-version') }}-1-${{ hashFiles('.github/depends.Rds') }} diff --git a/DESCRIPTION b/DESCRIPTION index def2d22..95db082 100644 --- a/DESCRIPTION +++ b/DESCRIPTION @@ -1,6 +1,6 @@ Package: Rogue Title: Identify Rogue Taxa in Sets of Phylogenetic Trees -Version: 2.1.6 +Version: 2.1.6.9000 Authors@R: c(person("Martin R.", 'Smith', email = "martin.smith@durham.ac.uk", role = c("aut", "cre", "cph"), diff --git a/NEWS.md b/NEWS.md index b37ae9c..fa48abd 100644 --- a/NEWS.md +++ b/NEWS.md @@ -1,4 +1,10 @@ -# Rogue v2.1.6 +# Rogue v2.1.6.9000 (2025-04-14) + +- Improve tip instability calculation in identical tree sets + ([#29](https://github.com/ms609/Rogue/issues/29)). + + +# Rogue v2.1.6 (2023-11-29) - Legend annotations in documentation. - Disable parallel evaluation by default in `TipInstability()`, @@ -6,37 +12,37 @@ - Use format string in REprintf(). -# Rogue v2.1.5 +# Rogue v2.1.5 (2023-03-20) - Call C functions using symbols, not strings. -# Rogue v2.1.4 +# Rogue v2.1.4 (2023-01-16) - C2X compliant function prototypes. - Remove unused `sprintf()` calls. -# Rogue v2.1.3 +# Rogue v2.1.3 (2022-09-26) - `ColByStability()` gains `pal` argument to allow specification of custom palettes. -# Rogue v2.1.2 +# Rogue v2.1.2 (2022-08-16) - Faster rogue detection when edge lengths provided, per report by Joe Keating. - Don't list `neverDrop` in `QuickRogue(fullSeq = TRUE)`. -# Rogue v2.1.1 +# Rogue v2.1.1 (2022-07-20) - Handle `ColByStability(trees = NULL)`. -# Rogue v2.1.0 +# Rogue v2.1.0 (2022-01-13) - Early termination of `QuickRogue()` when no further improvement possible. @@ -49,11 +55,11 @@ - New vignette detailing rogue detection with Bayesian tree samples. -# Rogue v2.0.0 +# Rogue v2.0.0 (2021-09-13) - Information theoretic rogue detection (per Smith, 2022). -# Rogue v1.0.0 +# Rogue v1.0.0 (2021-06-28) - R interface to RogueNaRok. diff --git a/R/stability.R b/R/stability.R index 445c6d8..cf3f9e5 100644 --- a/R/stability.R +++ b/R/stability.R @@ -183,7 +183,13 @@ ColByStability <- function(trees, log = TRUE, score <- TipInstability(trees, log = log, average = average, deviation = deviation) score <- score - min(score) - score <- score / max(score) + zero <- abs(score) < sqrt(.Machine$double.eps) + if (any(!zero)) { + score[zero] <- 0 + score <- score / max(score) + } else { + score[] <- 0 + } # Return: setNames(pal[1 + (score * (length(pal) - 1))], diff --git a/tests/testthat/test-stability.R b/tests/testthat/test-stability.R index 0437522..ebb645a 100644 --- a/tests/testthat/test-stability.R +++ b/tests/testthat/test-stability.R @@ -27,6 +27,9 @@ test_that("GraphGeodesic() works", { Test(PectinateTree(7)) Test(CollapseNode(BalancedTree(101), 104:111)) Test(as.phylo(201, 1201)) + + expect_equal(GraphGeodesic(BalancedTree(4), log = FALSE), + GraphGeodesic(BalancedTree(4), log = 1)) }) test_that("ColByStability()", { @@ -38,3 +41,11 @@ test_that("ColByStability()", { expect_equal(tipCol["t2"], tipCol["t1"]) }) +test_that("ColByStability() - stable trees", { + trees <- c(BalancedTree(4), BalancedTree(4), BalancedTree(4)) + cons <- Consensus(trees) + tipCols <- ColByStability(trees)[cons$tip.label] + expect_equal(tipCols, setNames(hcl.colors(131, "inferno")[rep(1, 4)], + cons[["tip.label"]])) +}) +