packages feed

elynx-seq 0.2.2 → 0.3.0

raw patch · 27 files changed

+1742/−1879 lines, 27 filesdep ~aesondep ~basedep ~bytestring

Dependency ranges changed: aeson, base, bytestring, containers, elynx-tools, hspec, hspec-megaparsec, matrices, megaparsec, mwc-random, parallel, primitive, vector, vector-th-unbox, word8

Files

ChangeLog.md view
@@ -2,6 +2,17 @@ # Changelog for ELynx  +## Version 0.3.1; in development+++## Version 0.3.0++-   **`elynx-nexus`:** library to import and export Nexus files.+-   **`elynx-tree`:** major refactor and big cleanup; use rose trees with branch+    labels.+-   **`elynx-tree`:** provide zippers.++ ## Version 0.2.2  -   Validation and repetition of previous analyses is finally possible with the
README.md view
@@ -2,9 +2,11 @@  # The ELynx Suite -Version: 0.2.2.+Version: 0.3.0. Reproducible evolution made easy. +<p align="center"><img src="https://travis-ci.org/dschrempf/elynx.svg?branch=master"/></p>+ A Haskell library and tool set for computational biology. The goal of ELynx is reproducible research. Evolutionary sequences and phylogenetic trees can be read, viewed, modified and simulated. The command line with all arguments is@@ -12,11 +14,12 @@ sums so that validation of past analyses is possible without the need to recompute the result. -The Elynx Suite consists of four library packages and three executables providing-a range of sub commands.+The Elynx Suite consists of library packages and executables providing a range+of sub commands.  The library packages are: +-   **elynx-nexus:** Nexus file support. -   **elynx-markov:** Simulate multi sequence alignments along phylogenetic trees. -   **elynx-seq:** Handle evolutionary sequences and multi sequence alignments. -   **elynx-tools:** Tools for the provided executables.@@ -43,7 +46,7 @@  2.  Clone the ELynx repository.     -        git clone clone https://github.com/dschrempf/elynx+        git clone https://github.com/dschrempf/elynx  3.  Navigate to the newly created `elynx` folder and build the binaries.     This will take a while.@@ -62,15 +65,34 @@     [PATH](https://en.wikipedia.org/wiki/PATH_(variable)) environment variable. Then, they can be used directly.  +# Documentation++Documentation is available on [Hackage](https://hackage.haskell.org/).++Libraries:++-   [elynx-nexus](https://hackage.haskell.org/package/elynx-nexus)+-   [elynx-markov](https://hackage.haskell.org/package/elynx-markov)+-   [elynx-seq](https://hackage.haskell.org/package/elynx-seq)+-   [elynx-tools](https://hackage.haskell.org/package/elynx-tools)+-   [elynx-tree](https://hackage.haskell.org/package/elynx-tree)++Executables:++-   [elynx](https://hackage.haskell.org/package/elynx)+-   [slynx](https://hackage.haskell.org/package/slynx)+-   [tlynx](https://hackage.haskell.org/package/tlynx)++ # SLynx  Handle evolutionary sequences. -    slynx --help+    slynx --help | head -n -16 -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: slynx [-v|--verbosity VALUE] [-o|--output-file-basename NAME]                   [-f|--force] COMMAND@@ -95,6 +117,7 @@       sub-sample               Sub-sample columns from multi sequence alignments.       translate                Translate from DNA to Protein or DNAX to ProteinX.     +         Available sequence file formats:       - FASTA     @@ -105,23 +128,6 @@       - Protein (amino acids)       - ProteinX (amino acids; including gaps)       - ProteinS (amino acids; including gaps, and translation stops)-      - ProteinI (amino acids; including gaps, translation stops, and IUPAC codes)-    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   ## Concatenate@@ -130,9 +136,9 @@      slynx concatenate --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: slynx concatenate (-a|--alphabet NAME) INPUT-FILE       Concatenate sequences found in input files.@@ -143,23 +149,6 @@       -a,--alphabet NAME       Specify alphabet type NAME       INPUT-FILE               Read sequences from INPUT-FILE       -h,--help                Show this help text-    -    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   ## Examine@@ -168,9 +157,9 @@      slynx examine --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: slynx examine (-a|--alphabet NAME) INPUT-FILE [--per-site]       Examine sequences. If data is a multi sequence alignment, additionally analyze columns.@@ -182,23 +171,6 @@       INPUT-FILE               Read sequences from INPUT-FILE       --per-site               Report per site summary statistics       -h,--help                Show this help text-    -    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   ## Filter@@ -207,9 +179,9 @@      slynx filter-rows --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: slynx filter-rows (-a|--alphabet NAME) INPUT-FILE [--longer-than LENGTH]                               [--shorter-than LENGTH] [--standard-characters]@@ -225,31 +197,14 @@       --standard-characters    Only keep sequences containing at least one standard                                (i.e., non-IUPAC) character       -h,--help                Show this help text-    -    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help  Filter columns of multi sequence alignments with `filter-columns`.      slynx filter-columns --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: slynx filter-columns (-a|--alphabet NAME) INPUT-FILE                                  [--standard-chars DOUBLE]@@ -263,23 +218,6 @@       --standard-chars DOUBLE  Keep columns with a proportion standard (non-IUPAC)                                characters larger than DOUBLE in [0,1]       -h,--help                Show this help text-    -    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   ## Simulate@@ -288,9 +226,9 @@      slynx simulate --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: slynx simulate (-t|--tree-file Name) [-s|--substitution-model MODEL]                            [-m|--mixture-model MODEL] [-e|--edm-file NAME] @@ -352,27 +290,13 @@        where XX is 10, 20, 30, 40, 50, or 60; CXX models, Quang et al., 2008.     -m "EDM(EXCHANGEABILITIES)"        Arbitrary empirical distribution mixture (EDM) models.-       Stationary distributions have to be provided with the -e option.+       Stationary distributions have to be provided with the -e or -p option.        For example,          LG exchangeabilities with stationary distributions given in FILE.          -m "EDM(LG-Custom)" -e FILE+         LG exchangeabilities with site profiles (Phylobayes) given in FILES.+         -m "EDM(LG-Custom)" -p FILES     For special mixture models, mixture weights are optional.-    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   ## Sub-sample@@ -381,9 +305,9 @@      slynx sub-sample --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: slynx sub-sample (-a|--alphabet NAME) INPUT-FILE                             (-n|--number-of-sites INT)@@ -403,22 +327,6 @@       -h,--help                Show this help text          Create a given number of multi sequence alignments, each of which contains a given number of random sites drawn from the original multi sequence alignment.-    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   ## Translate@@ -427,9 +335,9 @@      slynx translate --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: slynx translate (-a|--alphabet NAME) INPUT-FILE (-r|--reading-frame INT)                            (-u|--universal-code CODE)@@ -444,34 +352,17 @@       -u,--universal-code CODE universal code; one of: Standard,                                VertebrateMitochondrial.       -h,--help                Show this help text-    -    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   # TLynx  Handle phylogenetic trees in Newick format. -    tlynx --help+    tlynx --help | head -n -16 -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: tlynx [-v|--verbosity VALUE] [-o|--output-file-basename NAME]                   [-f|--force] COMMAND@@ -496,26 +387,10 @@       shuffle                  Shuffle a phylogenetic tree (keep coalescent times, but shuffle topology and leaves).       simulate                 Simulate phylogenetic trees using birth and death processes (see also the 'coalesce' command for simulations using the coalescent process).     +         Available tree file formats:       - Newick Standard: Branch support values are stored in square brackets after branch lengths.       - Newick IqTree:   Branch support values are stored as node names after the closing bracket of forests.-      - Newick RevBayes  Key-value pairs is provided in square brackets after node names as well as branch lengths. XXX: Key value pairs are IGNORED at the moment.-    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   ## Compare@@ -524,12 +399,12 @@      tlynx compare --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: tlynx compare [-n|--normalize] [-b|--bipartitions] [-t|--intersect] -                         [-f|--newick-format FORMAT] NAME+                         [-f|--newick-format FORMAT] NAMES       Compare two phylogenetic trees (compute distances and branch-wise differences).          Available options:@@ -540,27 +415,11 @@       -t,--intersect           Compare intersections; i.e., before comparison, drop                                leaves that are not present in the other tree       -f,--newick-format FORMAT-                               Newick tree format; see 'tlynx-                               --help' (default: Standard)-      NAME                     Tree file+                               Newick tree format: Standard, IqTree, or RevBayes;+                               default: Standard; for detailed help, see 'tlynx+                               --help'+      NAMES                    Tree files       -h,--help                Show this help text-    -    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   ## Examine@@ -569,9 +428,9 @@      tlynx examine --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: tlynx examine INPUT-FILE [-f|--newick-format FORMAT]       Compute summary statistics of phylogenetic trees.@@ -581,26 +440,10 @@       -V,--version             Show version       INPUT-FILE               Read trees from INPUT-FILE       -f,--newick-format FORMAT-                               Newick tree format; see 'tlynx-                               --help' (default: Standard)+                               Newick tree format: Standard, IqTree, or RevBayes;+                               default: Standard; for detailed help, see 'tlynx+                               --help'       -h,--help                Show this help text-    -    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   ## Simulate@@ -609,9 +452,9 @@      tlynx simulate --help -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: tlynx simulate [-t|--nTrees INT] [-n|--nLeaves INT] [-H|--height DOUBLE]                            [-M|--condition-on-mrca] [-l|--lambda DOUBLE] @@ -640,33 +483,17 @@     Summary statistics only: only print (NumberOfExtantChildren BranchLength) pairs for each branch of each tree. The trees are separated by a newline character.     Sub-sampling: simulate one big tree with n'=round(n/rho), n'>=n, leaves, and randomly sample sub-trees with n leaves. Hence, with rho=1.0, the same tree is reported over and over again.     Gernhard, T. (2008). The conditioned reconstructed process. Journal of Theoretical Biology, 253(4), 769–778. http://doi.org/10.1016/j.jtbi.2008.04.005-    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help   # ELynx  Validate and (optionally) redo past ELynx analyses. -    elynx --help+    elynx --help | head -n -16 -    ELynx Suite version 0.2.1.+    ELynx Suite version 0.3.0.     Developed by Dominik Schrempf.-    Compiled on April 27, 2020, at 12:08 pm, UTC.+    Compiled on July 30, 2020, at 12:40 pm, UTC.          Usage: elynx COMMAND       Validate and redo past ELynx analyses@@ -678,37 +505,4 @@     Available commands:       validate                 Validate an ELynx analysis       redo                     Redo an ELynx analysis-    -    -    ELynx-    ------    A Haskell library and tool set for computational biology. The goal of ELynx is-    reproducible research. Evolutionary sequences and phylogenetic trees can be-    read, viewed, modified and simulated. The command line with all arguments is-    logged consistently, and automatically. Data integrity is verified using SHA256-    sums so that validation of past analyses is possible without the need to-    recompute the result.-    -    slynx     Analyze, modify, and simulate evolutionary sequences.-    tlynx     Analyze, modify, and simulate phylogenetic trees.-    elynx     Validate and redo past analyses.-    -    Get help for sub commands:-      slynx examine --help---# Library documentation--Documentation of the libraries can be found on [Hackage](https://hackage.haskell.org/):---   [elynx-markov](https://hackage.haskell.org/package/elynx-markov)--   [elynx-seq](https://hackage.haskell.org/package/elynx-seq)--   [elynx-tools](https://hackage.haskell.org/package/elynx-tools)--   [elynx-tree](https://hackage.haskell.org/package/elynx-tree)--Documentation of the executables is also available:---   [elynx](https://hackage.haskell.org/package/elynx)--   [slynx](https://hackage.haskell.org/package/slynx)--   [tlynx](https://hackage.haskell.org/package/tlynx) 
elynx-seq.cabal view
@@ -1,94 +1,96 @@-cabal-version: 1.12-name: elynx-seq-version: 0.2.2-license: GPL-3-license-file: LICENSE-copyright: Dominik Schrempf (2020)-maintainer: dominik.schrempf@gmail.com-author: Dominik Schrempf-homepage: https://github.com/dschrempf/elynx#readme-bug-reports: https://github.com/dschrempf/elynx/issues-synopsis: Handle molecular sequences-description:-    Examine, modify, and simulate molecular sequences in a reproducible way. Please see the README on GitHub at <https://github.com/dschrempf/elynx>.-category: Bioinformatics-build-type: Simple+cabal-version: 2.2++-- This file has been generated from package.yaml by hpack version 0.34.2.+--+-- see: https://github.com/sol/hpack+--+-- hash: afdff7b344d4b63f734a6f18db88ef39b1f45ed84c64e63045b57edfb839684f++name:           elynx-seq+version:        0.3.0+synopsis:       Handle molecular sequences+description:    Examine, modify, and simulate molecular sequences in a reproducible way. Please see the README on GitHub at <https://github.com/dschrempf/elynx>.+category:       Bioinformatics+homepage:       https://github.com/dschrempf/elynx#readme+bug-reports:    https://github.com/dschrempf/elynx/issues+author:         Dominik Schrempf+maintainer:     dominik.schrempf@gmail.com+copyright:      Dominik Schrempf (2020)+license:        GPL-3.0-or-later+license-file:   LICENSE+build-type:     Simple extra-source-files:     README.md     ChangeLog.md  source-repository head-    type: git-    location: https://github.com/dschrempf/elynx+  type: git+  location: https://github.com/dschrempf/elynx  library-    exposed-modules:-        ELynx.Data.Alphabet.Alphabet-        ELynx.Data.Alphabet.Character-        ELynx.Data.Alphabet.DistributionDiversity-        ELynx.Data.Character.AminoAcid-        ELynx.Data.Character.AminoAcidI-        ELynx.Data.Character.AminoAcidS-        ELynx.Data.Character.AminoAcidX-        ELynx.Data.Character.Character-        ELynx.Data.Character.Codon-        ELynx.Data.Character.Nucleotide-        ELynx.Data.Character.NucleotideI-        ELynx.Data.Character.NucleotideX-        ELynx.Data.Sequence.Alignment-        ELynx.Data.Sequence.Defaults-        ELynx.Data.Sequence.Sequence-        ELynx.Data.Sequence.Translate-        ELynx.Export.Sequence.Fasta-        ELynx.Import.Sequence.Fasta-    hs-source-dirs: src-    other-modules:-        Paths_elynx_seq-    default-language: Haskell2010-    ghc-options: -Wall -fllvm-    build-depends:-        aeson >=1.4.7.1 && <1.5,-        base >=4.13.0.0 && <4.14,-        bytestring >=0.10.10.0 && <0.11,-        containers >=0.6.2.1 && <0.7,-        elynx-tools >=0.2.2 && <0.3,-        matrices >=0.5.0 && <0.6,-        megaparsec >=8.0.0 && <8.1,-        mwc-random >=0.14.0.0 && <0.15,-        parallel >=3.2.2.0 && <3.3,-        primitive >=0.7.0.1 && <0.8,-        vector >=0.12.1.2 && <0.13,-        vector-th-unbox >=0.2.1.7 && <0.3,-        word8 >=0.1.3 && <0.2+  exposed-modules:+      ELynx.Data.Alphabet.Alphabet+      ELynx.Data.Alphabet.Character+      ELynx.Data.Alphabet.DistributionDiversity+      ELynx.Data.Character.AminoAcid+      ELynx.Data.Character.AminoAcidI+      ELynx.Data.Character.AminoAcidS+      ELynx.Data.Character.AminoAcidX+      ELynx.Data.Character.Character+      ELynx.Data.Character.Codon+      ELynx.Data.Character.Nucleotide+      ELynx.Data.Character.NucleotideI+      ELynx.Data.Character.NucleotideX+      ELynx.Data.Sequence.Alignment+      ELynx.Data.Sequence.Defaults+      ELynx.Data.Sequence.Sequence+      ELynx.Data.Sequence.Translate+      ELynx.Export.Sequence.Fasta+      ELynx.Import.Sequence.Fasta+  other-modules:+      Paths_elynx_seq+  autogen-modules:+      Paths_elynx_seq+  hs-source-dirs:+      src+  ghc-options: -Wall -fllvm+  build-depends:+      aeson+    , base >=4.7 && <5+    , bytestring+    , containers+    , elynx-tools+    , matrices+    , megaparsec+    , mwc-random+    , parallel+    , primitive+    , vector+    , vector-th-unbox+    , word8+  default-language: Haskell2010  test-suite seq-test-    type: exitcode-stdio-1.0-    main-is: Spec.hs-    hs-source-dirs: test-    other-modules:-        ELynx.Data.Alphabet.DistributionDiversitySpec-        ELynx.Data.Sequence.AlignmentSpec-        ELynx.Data.Sequence.SequenceSpec-        ELynx.Data.Sequence.TranslateSpec-        ELynx.Export.Sequence.FastaSpec-        ELynx.Import.Sequence.FastaSpec-        Paths_elynx_seq-    default-language: Haskell2010-    ghc-options: -Wall -fllvm -threaded -rtsopts -with-rtsopts=-N-    build-depends:-        aeson >=1.4.7.1 && <1.5,-        base >=4.13.0.0 && <4.14,-        bytestring >=0.10.10.0 && <0.11,-        containers >=0.6.2.1 && <0.7,-        elynx-seq -any,-        elynx-tools >=0.2.2 && <0.3,-        hspec >=2.7.1 && <2.8,-        hspec-megaparsec >=2.1.0 && <2.2,-        matrices >=0.5.0 && <0.6,-        megaparsec >=8.0.0 && <8.1,-        mwc-random >=0.14.0.0 && <0.15,-        parallel >=3.2.2.0 && <3.3,-        primitive >=0.7.0.1 && <0.8,-        vector >=0.12.1.2 && <0.13,-        vector-th-unbox >=0.2.1.7 && <0.3,-        word8 >=0.1.3 && <0.2+  type: exitcode-stdio-1.0+  main-is: Spec.hs+  other-modules:+      ELynx.Data.Alphabet.DistributionDiversitySpec+      ELynx.Data.Sequence.AlignmentSpec+      ELynx.Data.Sequence.SequenceSpec+      ELynx.Data.Sequence.TranslateSpec+      ELynx.Export.Sequence.FastaSpec+      ELynx.Import.Sequence.FastaSpec+      Paths_elynx_seq+  hs-source-dirs:+      test+  ghc-options: -Wall -fllvm+  build-depends:+      base >=4.7 && <5+    , bytestring+    , elynx-seq+    , elynx-tools+    , hspec+    , hspec-megaparsec+    , matrices+    , vector+  default-language: Haskell2010
src/ELynx/Data/Alphabet/Alphabet.hs view
@@ -1,62 +1,65 @@ {-# LANGUAGE DeriveGeneric #-} -{- |-Module      :  ELynx.Data.Alphabet.Alphabet-Description :  Alphabets store hereditary information-Copyright   :  (c) Dominik Schrempf 2020-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable--Portability :  portable--Creation date: Fri May 10 11:10:32 2019.--Hierarchy:--1. 'Character' type.--2. Sets of 'Character's form 'Alphabet's; each 'Alphabet' has a specification-'AlphabetSpec'.--New alphabets have to be added manually in this module.--This way of handling characters and alphabets IS NOT TYPE SAFE, but much, much-faster. A second layer of modules such as 'ELynx.Data.Character.Nucleotide'-depend on a 'ELynx.Data.Character.Character.Character' type class. Hence, they-provide a type safe way of handling alphabets. Conversion is possible, for-instance, with 'ELynx.Data.Alphabet.Character.fromCVec', and-'ELynx.Data.Alphabet.Character.toCVec'.---}-+-- |+-- Module      :  ELynx.Data.Alphabet.Alphabet+-- Description :  Alphabets store hereditary information+-- Copyright   :  (c) Dominik Schrempf 2020+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+--+-- Portability :  portable+--+-- Creation date: Fri May 10 11:10:32 2019.+--+-- Hierarchy:+--+-- 1. 'Character' type.+--+-- 2. Sets of 'Character's form 'Alphabet's; each 'Alphabet' has a specification+-- 'AlphabetSpec'.+--+-- New alphabets have to be added manually in this module.+--+-- This way of handling characters and alphabets IS NOT TYPE SAFE, but much, much+-- faster. A second layer of modules such as 'ELynx.Data.Character.Nucleotide'+-- depend on a 'ELynx.Data.Character.Character.Character' type class. Hence, they+-- provide a type safe way of handling alphabets. Conversion is possible, for+-- instance, with 'ELynx.Data.Alphabet.Character.fromCVec', and+-- 'ELynx.Data.Alphabet.Character.toCVec'. module ELynx.Data.Alphabet.Alphabet-  ( Alphabet(..)-  , AlphabetSpec(..)-  , alphabetSpec-  , alphabetDescription-  , isStd-  , isGap-  , isUnknown-  , isIUPAC-  , isMember+  ( Alphabet (..),+    AlphabetSpec (..),+    alphabetSpec,+    alphabetDescription,+    isStd,+    isGap,+    isUnknown,+    isIUPAC,+    isMember,   ) where -import qualified Data.Set                      as S-import           Prelude                 hiding ( all )-import           Data.Aeson                     ( FromJSON-                                                , ToJSON-                                                )-import           GHC.Generics                   ( Generic )--import           ELynx.Data.Alphabet.Character+import Data.Aeson+  ( FromJSON,+    ToJSON,+  )+import qualified Data.Set as S+import ELynx.Data.Alphabet.Character+import GHC.Generics (Generic)+import Prelude hiding (all)  -- | Available alphabets; for details see 'alphabetSpec'.-data Alphabet = DNA | DNAX | DNAI-              | Protein | ProteinX | ProteinS | ProteinI-              deriving (Show, Read, Eq, Ord, Enum, Bounded, Generic)+data Alphabet+  = DNA+  | DNAX+  | DNAI+  | Protein+  | ProteinX+  | ProteinS+  | ProteinI+  deriving (Show, Read, Eq, Ord, Enum, Bounded, Generic)  instance FromJSON Alphabet @@ -64,11 +67,11 @@  -- | Verbose alphabet name. alphabetDescription :: Alphabet -> String-alphabetDescription DNA  = "DNA (nucleotides)"+alphabetDescription DNA = "DNA (nucleotides)" alphabetDescription DNAX = "DNAX (nucleotides; including gaps)" alphabetDescription DNAI =   "DNAI (nucleotides; including gaps, and IUPAC codes)"-alphabetDescription Protein  = "Protein (amino acids)"+alphabetDescription Protein = "Protein (amino acids)" alphabetDescription ProteinX = "ProteinX (amino acids; including gaps)" alphabetDescription ProteinS =   "ProteinS (amino acids; including gaps, and translation stops)"@@ -76,27 +79,45 @@   "ProteinI (amino acids; including gaps, translation stops, and IUPAC codes)"  -- | Alphabet specification. 'S.Set' is used because it provides fast lookups.-data AlphabetSpec = AlphabetSpec {-  -- | Standard characters.-  std       :: !(S.Set Character)-  -- | Gap characters.-  , gap     :: !(S.Set Character)-  -- | Unknown characters.-  , unknown :: !(S.Set Character)-  -- | Other IUPAC codes.-  , iupac   :: !(S.Set Character)-  -- | All characters in the alphabet.-  , all     :: !(S.Set Character)-  -- | Convert from IUPAC to the corresponding standard characters.-  , toStd   :: Character -> [Character]+data AlphabetSpec = AlphabetSpec+  { -- | Standard characters.+    std :: !(S.Set Character),+    -- | Gap characters.+    gap :: !(S.Set Character),+    -- | Unknown characters.+    unknown :: !(S.Set Character),+    -- | Other IUPAC codes.+    iupac :: !(S.Set Character),+    -- | All characters in the alphabet.+    all :: !(S.Set Character),+    -- | Convert from IUPAC to the corresponding standard characters.+    toStd :: Character -> [Character]   } +-- Create alphabet spec.+fromChars ::+  String -> String -> String -> String -> (Char -> String) -> AlphabetSpec+fromChars st ga un iu to =+  AlphabetSpec+    st'+    ga'+    un'+    iu'+    al+    (fromString . to . toChar)+  where+    st' = S.fromList $ fromString st+    ga' = S.fromList $ fromString ga+    un' = S.fromList $ fromString un+    iu' = S.fromList $ fromString iu+    al = S.unions [st', ga', un', iu']+ -- | Get the alphabet specification for a given alphabet. alphabetSpec :: Alphabet -> AlphabetSpec-alphabetSpec DNA      = dna-alphabetSpec DNAX     = dnaX-alphabetSpec DNAI     = dnaI-alphabetSpec Protein  = protein+alphabetSpec DNA = dna+alphabetSpec DNAX = dnaX+alphabetSpec DNAI = dnaI+alphabetSpec Protein = protein alphabetSpec ProteinX = proteinX alphabetSpec ProteinS = proteinS alphabetSpec ProteinI = proteinI@@ -124,21 +145,6 @@ isMember :: Alphabet -> Character -> Bool isMember = isWith all -fromChars-  :: String -> String -> String -> String -> (Char -> String) -> AlphabetSpec-fromChars st ga un iu to = AlphabetSpec st'-                                        ga'-                                        un'-                                        iu'-                                        al-                                        (fromString . to . toChar)- where-  st' = S.fromList $ fromString st-  ga' = S.fromList $ fromString ga-  un' = S.fromList $ fromString un-  iu' = S.fromList $ fromString iu-  al  = S.unions [st', ga', un', iu']- dna :: AlphabetSpec dna = fromChars "ACGT" [] [] [] toStdDNA @@ -147,7 +153,7 @@ toStdDNA 'C' = "C" toStdDNA 'G' = "G" toStdDNA 'T' = "T"-toStdDNA _   = error "tostdDNA: Cannot convert to standard nucleotide."+toStdDNA _ = error "tostdDNA: Cannot convert to standard nucleotide."  dnaX :: AlphabetSpec dnaX = fromChars "ACGT" "-." [] [] toStdDNAX@@ -159,10 +165,10 @@ toStdDNAX 'T' = "T" toStdDNAX '-' = [] toStdDNAX '.' = []-toStdDNAX _   = error "toStdDNAX: Cannot convert to standard nucleotide."+toStdDNAX _ = error "toStdDNAX: Cannot convert to standard nucleotide."  dnaI :: AlphabetSpec-dnaI = fromChars "ACGT" "-." "N" "UWSMKRYBDHV" toStdDNAI+dnaI = fromChars "ACGT" "-." "N?" "UWSMKRYBDHV" toStdDNAI  toStdDNAI :: Char -> String toStdDNAI 'A' = "A"@@ -181,9 +187,10 @@ toStdDNAI 'H' = "ACT" toStdDNAI 'V' = "ACG" toStdDNAI 'N' = "ACGT"+toStdDNAI '?' = "ACGT" toStdDNAI '-' = [] toStdDNAI '.' = []-toStdDNAI _   = error "toStdDNAI: Cannot convert to standard nucleotide."+toStdDNAI _ = error "toStdDNAI: Cannot convert to standard nucleotide."  protein :: AlphabetSpec protein = fromChars "ACDEFGHIKLMNPQRSTVWY" [] [] [] toStdP@@ -209,7 +216,7 @@ toStdP 'V' = "V" toStdP 'W' = "W" toStdP 'Y' = "Y"-toStdP _   = error "toStdP: Cannot convert to standard amino acid."+toStdP _ = error "toStdP: Cannot convert to standard amino acid."  proteinX :: AlphabetSpec proteinX = fromChars "ACDEFGHIKLMNPQRSTVWY" "-." [] [] toStdPX@@ -237,7 +244,7 @@ toStdPX 'Y' = "Y" toStdPX '-' = "" toStdPX '.' = ""-toStdPX _   = error "toStdPX: Cannot convert to standard amino acid."+toStdPX _ = error "toStdPX: Cannot convert to standard amino acid."  proteinS :: AlphabetSpec proteinS = fromChars "ACDEFGHIKLMNPQRSTVWY" "-." [] "*" toStdPS@@ -266,10 +273,10 @@ toStdPS '-' = "" toStdPS '.' = "" toStdPS '*' = ""-toStdPS _   = error "toStdPX: Cannot convert to standard amino acid."+toStdPS _ = error "toStdPX: Cannot convert to standard amino acid."  proteinI :: AlphabetSpec-proteinI = fromChars "ACDEFGHIKLMNPQRSTVWY" "-." "X" "*JBZ" toStdPI+proteinI = fromChars "ACDEFGHIKLMNPQRSTVWY" "-." "X?" "*JBZ" toStdPI  toStdPI :: Char -> String toStdPI 'A' = "A"@@ -299,4 +306,5 @@ toStdPI 'B' = "DN" toStdPI 'Z' = "EQ" toStdPI 'X' = "ACDEFGHIKLMNPQRSTVWY"-toStdPI _   = error "toStdPX: Cannot convert to standard amino acid."+toStdPI '?' = "ACDEFGHIKLMNPQRSTVWY"+toStdPI _ = error "toStdPX: Cannot convert to standard amino acid."
src/ELynx/Data/Alphabet/Character.hs view
@@ -1,41 +1,36 @@ {-# LANGUAGE MultiParamTypeClasses #-}-{-# LANGUAGE TemplateHaskell       #-}-{-# LANGUAGE TypeFamilies          #-}--{- |-Module      :  ELynx.Data.Alphabet.Character-Description :  Alphabet characters-Copyright   :  (c) Dominik Schrempf 2020-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Sun May 19 21:06:38 2019.---}+{-# LANGUAGE TemplateHaskell #-}+{-# LANGUAGE TypeFamilies #-} +-- |+-- Module      :  ELynx.Data.Alphabet.Character+-- Description :  Alphabet characters+-- Copyright   :  (c) Dominik Schrempf 2020+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Sun May 19 21:06:38 2019. module ELynx.Data.Alphabet.Character-  ( Character-  , toWord-  , fromWord-  , toChar-  , fromChar-  , toString-  , fromString-  , toCVec-  , fromCVec+  ( Character,+    toWord,+    fromWord,+    toChar,+    fromChar,+    toString,+    fromString,+    toCVec,+    fromCVec,   ) where -import qualified Data.Vector.Unboxed           as V-import           Data.Vector.Unboxed.Deriving-import           Data.Word8--import qualified ELynx.Data.Character.Character-                                               as C-import           ELynx.Tools+import qualified Data.Vector.Unboxed as V+import Data.Vector.Unboxed.Deriving+import Data.Word8+import qualified ELynx.Data.Character.Character as C+import ELynx.Tools  -- | Alphabet characters; abstracted so that representation can be changed at -- some point.@@ -74,8 +69,8 @@ fromCVec :: C.Character a => V.Vector a -> V.Vector Character fromCVec = V.map (fromWord . C.toWord) -derivingUnbox "Character"-    [t| Character -> Word8 |]-    [| \(Character w) -> w |]-    [| Character |]-+derivingUnbox+  "Character"+  [t|Character -> Word8|]+  [|\(Character w) -> w|]+  [|Character|]
src/ELynx/Data/Alphabet/DistributionDiversity.hs view
@@ -1,48 +1,50 @@ {-# LANGUAGE FlexibleContexts #-} -{- |-Module      :  ELynx.Data.Alphabet.DistributionDiversity-Description :  Summarize statistics for alphabets-Copyright   :  (c) Dominik Schrempf 2020-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Mon Feb 25 13:32:56 2019.---}-+-- |+-- Module      :  ELynx.Data.Alphabet.DistributionDiversity+-- Description :  Summarize statistics for alphabets+-- Copyright   :  (c) Dominik Schrempf 2020+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Mon Feb 25 13:32:56 2019. module ELynx.Data.Alphabet.DistributionDiversity   ( -- * Entropy-    entropy-  , kEffEntropy+    entropy,+    kEffEntropy,+     -- * Homoplasy-  , homoplasy-  , kEffHomoplasy+    homoplasy,+    kEffHomoplasy,+     -- * Count characters-  , frequencyCharacters+    frequencyCharacters,   ) where -import qualified Data.Set                      as S-import qualified Data.Vector.Generic           as V-import           Data.Vector.Generic            ( Vector-                                                , toList-                                                )--import           ELynx.Data.Alphabet.Alphabet-import           ELynx.Data.Alphabet.Character-import           ELynx.Tools+import qualified Data.Set as S+import Data.Vector.Generic+  ( Vector,+    toList,+  )+import qualified Data.Vector.Generic as V+import ELynx.Data.Alphabet.Alphabet+import ELynx.Data.Alphabet.Character+import ELynx.Tools  -- | Entropy of vector. entropy :: (Vector v Double) => v Double -> Double-entropy v = if isNaN res-  then error-    ("entropy: Sesult of following vector is NaN: " ++ show (toList v) ++ ".")-  else res-  where res = negate $ sumVec $ V.map xLogX v+entropy v =+  if isNaN res+    then+      error+        ("entropy: Sesult of following vector is NaN: " ++ show (toList v) ++ ".")+    else res+  where+    res = negate $ sumVec $ V.map xLogX v  -- | Effective number of used characters measured using 'entropy'. The result -- only makes sense when the sum of the array is 1.0.@@ -64,19 +66,21 @@ -- Increment element at index in vector by one. incrementElemIndexByOne :: Vector v Int => [Int] -> v Int -> v Int incrementElemIndexByOne is v = v V.// zip is es'-  where es' = [ v V.! i + 1 | i <- is ]+  where+    es' = [v V.! i + 1 | i <- is]  -- For a given code and counts vector, increment the count of the given character. acc :: Vector v Int => AlphabetSpec -> v Int -> Character -> v Int acc alph vec char = incrementElemIndexByOne is vec-  where is = [ S.findIndex c (std alph) | c <- toStd alph char ]+  where+    is = [S.findIndex c (std alph) | c <- toStd alph char] -countCharacters-  :: (Vector v Character, Vector v Int) => AlphabetSpec -> v Character -> v Int+countCharacters ::+  (Vector v Character, Vector v Int) => AlphabetSpec -> v Character -> v Int countCharacters alph = V.foldl' (acc alph) zeroCounts- where-  nChars     = length (std alph)-  zeroCounts = V.replicate nChars (0 :: Int)+  where+    nChars = length (std alph)+    zeroCounts = V.replicate nChars (0 :: Int)  saveDivision :: Int -> Int -> Double saveDivision value divisor =@@ -86,12 +90,12 @@ -- The input vector has arbitrary length (most often the number of sequences in -- an alignment), the length of the output vector is the number of characters in -- the alphabet.-frequencyCharacters-  :: (Vector v Character, Vector v Int, Vector v Double)-  => AlphabetSpec-  -> v Character-  -> v Double+frequencyCharacters ::+  (Vector v Character, Vector v Int, Vector v Double) =>+  AlphabetSpec ->+  v Character ->+  v Double frequencyCharacters alph d = V.map (`saveDivision` s) counts- where-  counts = countCharacters alph d-  s      = sumVec counts+  where+    counts = countCharacters alph d+    s = sumVec counts
src/ELynx/Data/Character/AminoAcid.hs view
@@ -1,61 +1,56 @@ {-# LANGUAGE MultiParamTypeClasses #-}-{-# LANGUAGE TemplateHaskell       #-}-{-# LANGUAGE TypeFamilies          #-}--{- |-Module      :  ELynx.Data.AminoAcid-Description :  Amino acid related types and functions-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Thu Oct  4 18:26:35 2018.--See header of 'ELynx.Data.Alphabet.Alphabet'.--Amino acids in alphabetical order.--@-Amino Acid Code:  Three letter Code:  Amino Acid:-----------------  ------------------  ------------A                 Ala                 Alanine-C                 Cys                 Cysteine-D                 Asp                 Aspartic Acid-E                 Glu                 Glutamic Acid-F                 Phe                 Phenylalanine-G                 Gly                 Glycine-H                 His                 Histidine-I                 Ile                 Isoleucine-K                 Lys                 Lysine-L                 Leu                 Leucine-M                 Met                 Methionine-N                 Asn                 Asparagine-P                 Pro                 Proline-Q                 Gln                 Glutamine-R                 Arg                 Arginine-S                 Ser                 Serine-T                 Thr                 Threonine-V                 Val                 Valine-W                 Trp                 Tryptophan-Y                 Tyr                 Tyrosine-@---}+{-# LANGUAGE TemplateHaskell #-}+{-# LANGUAGE TypeFamilies #-} +-- |+-- Module      :  ELynx.Data.AminoAcid+-- Description :  Amino acid related types and functions+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Thu Oct  4 18:26:35 2018.+--+-- See header of 'ELynx.Data.Alphabet.Alphabet'.+--+-- Amino acids in alphabetical order.+--+-- @+-- Amino Acid Code:  Three letter Code:  Amino Acid:+-- ----------------  ------------------  -----------+-- A                 Ala                 Alanine+-- C                 Cys                 Cysteine+-- D                 Asp                 Aspartic Acid+-- E                 Glu                 Glutamic Acid+-- F                 Phe                 Phenylalanine+-- G                 Gly                 Glycine+-- H                 His                 Histidine+-- I                 Ile                 Isoleucine+-- K                 Lys                 Lysine+-- L                 Leu                 Leucine+-- M                 Met                 Methionine+-- N                 Asn                 Asparagine+-- P                 Pro                 Proline+-- Q                 Gln                 Glutamine+-- R                 Arg                 Arginine+-- S                 Ser                 Serine+-- T                 Thr                 Threonine+-- V                 Val                 Valine+-- W                 Trp                 Tryptophan+-- Y                 Tyr                 Tyrosine+-- @ module ELynx.Data.Character.AminoAcid-  ( AminoAcid(..)+  ( AminoAcid (..),   ) where -import           Data.Vector.Unboxed.Deriving-import           Data.Word8--import qualified ELynx.Data.Character.Character-                                               as C-import           ELynx.Tools+import Data.Vector.Unboxed.Deriving+import Data.Word8+import qualified ELynx.Data.Character.Character as C+import ELynx.Tools  -- | Amino acids. data AminoAcid = A | C | D | E | F | G | H | I | K | L | M | N | P | Q | R | S | T | V | W | Y@@ -105,13 +100,14 @@   'V' -> V   'W' -> W   'Y' -> Y-  _   -> error "fromWord: Cannot convert to AminoAcid."+  _ -> error "fromWord: Cannot convert to AminoAcid." -derivingUnbox "AminoAcid"-    [t| AminoAcid -> Word8 |]-    [| toWord |]-    [| fromWord |]+derivingUnbox+  "AminoAcid"+  [t|AminoAcid -> Word8|]+  [|toWord|]+  [|fromWord|]  instance C.Character AminoAcid where-  toWord   = toWord+  toWord = toWord   fromWord = fromWord
src/ELynx/Data/Character/AminoAcidI.hs view
@@ -1,109 +1,135 @@ {-# LANGUAGE MultiParamTypeClasses #-}-{-# LANGUAGE TemplateHaskell       #-}-{-# LANGUAGE TypeFamilies          #-}--{- |-Module      :  ELynx.Data.AminoAcid-Description :  Amino acid related types and functions-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Thu Oct  4 18:26:35 2018.--See header of 'ELynx.Data.Alphabet.Alphabet'.--Amino acid IUPAC code. See also https://www.bioinformatics.org/sms/iupac.html or-https://en.wikipedia.org/wiki/International_Union_of_Pure_and_Applied_Chemistry.--@-Amino Acid Code:  Three letter Code:  Amino Acid:-----------------  ------------------  ------------A                 Ala                 Alanine-C                 Cys                 Cysteine-D                 Asp                 Aspartic Acid-E                 Glu                 Glutamic Acid-F                 Phe                 Phenylalanine-G                 Gly                 Glycine-H                 His                 Histidine-I                 Ile                 Isoleucine-K                 Lys                 Lysine-L                 Leu                 Leucine-M                 Met                 Methionine-N                 Asn                 Asparagine-P                 Pro                 Proline-Q                 Gln                 Glutamine-R                 Arg                 Arginine-S                 Ser                 Serine-T                 Thr                 Threonine-V                 Val                 Valine-W                 Trp                 Tryptophan-Y                 Tyr                 Tyrosine-------------------J                                     Leucine or Isoleucine-B                 Asx                 Aspartic acid or Asparagine-Z                 Glx                 Glutamine or Glutamic acid-------------------X                 Xaa                 Any amino acid-------------------*                 Stp                 No amino acid--------------------                 Gap                 No amino acid-.                 Gap                 No amino acid-@---}+{-# LANGUAGE TemplateHaskell #-}+{-# LANGUAGE TypeFamilies #-} +-- |+-- Module      :  ELynx.Data.AminoAcid+-- Description :  Amino acid related types and functions+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Thu Oct  4 18:26:35 2018.+--+-- See header of 'ELynx.Data.Alphabet.Alphabet'.+--+-- Amino acid IUPAC code. See also https://www.bioinformatics.org/sms/iupac.html or+-- https://en.wikipedia.org/wiki/International_Union_of_Pure_and_Applied_Chemistry.+--+-- Remarks:+--+-- - Question marks (@?@) are interpreted as unknowns (same as @X@). However, when+--   a sequence is printed/exported, @X@s will be used.+--+-- - Full stops (@.@) are interpreted as gaps (same as @-@). However, when a+--   sequence is printed/exported, @-@s will be used+--+-- @+-- Amino Acid Code:  Three letter Code:  Amino Acid:+-- ----------------  ------------------  -----------+-- A                 Ala                 Alanine+-- C                 Cys                 Cysteine+-- D                 Asp                 Aspartic Acid+-- E                 Glu                 Glutamic Acid+-- F                 Phe                 Phenylalanine+-- G                 Gly                 Glycine+-- H                 His                 Histidine+-- I                 Ile                 Isoleucine+-- K                 Lys                 Lysine+-- L                 Leu                 Leucine+-- M                 Met                 Methionine+-- N                 Asn                 Asparagine+-- P                 Pro                 Proline+-- Q                 Gln                 Glutamine+-- R                 Arg                 Arginine+-- S                 Ser                 Serine+-- T                 Thr                 Threonine+-- V                 Val                 Valine+-- W                 Trp                 Tryptophan+-- Y                 Tyr                 Tyrosine+-- ----------------  ------------------  -----------+-- J                                     Leucine or Isoleucine+-- B                 Asx                 Aspartic acid or Asparagine+-- Z                 Glx                 Glutamine or Glutamic acid+-- ----------------  ------------------  -----------+-- X                 Xaa                 Any amino acid (preferred; used for printing)+-- ?                 Xaa                 Any amino acid+-- ----------------  ------------------  -----------+-- *                 Stp                 No amino acid+-- ----------------  ------------------  -----------+-- -                 Gap                 No amino acid (preferred; used for printing)+-- .                 Gap                 No amino acid+-- @ module ELynx.Data.Character.AminoAcidI-  ( AminoAcidI(..)+  ( AminoAcidI (..),   ) where -import           Data.Vector.Unboxed.Deriving-import           Data.Word8--import qualified ELynx.Data.Character.Character-                                               as C-import           ELynx.Tools+import Data.Vector.Unboxed.Deriving+import Data.Word8+import qualified ELynx.Data.Character.Character as C+import ELynx.Tools  -- | Amino acids.-data AminoAcidI = A | C | D | E | F | G | H | I | K | L | M | N | P | Q | R | S | T | V | W | Y-                | J | B | Z-                | X-                | Stop-                | Gap+data AminoAcidI+  = A+  | C+  | D+  | E+  | F+  | G+  | H+  | I+  | K+  | L+  | M+  | N+  | P+  | Q+  | R+  | S+  | T+  | V+  | W+  | Y+  | J+  | B+  | Z+  | X+  | Stop+  | Gap   deriving (Show, Read, Eq, Ord, Enum, Bounded)  toWord :: AminoAcidI -> Word8-toWord A    = c2w 'A'-toWord C    = c2w 'C'-toWord D    = c2w 'D'-toWord E    = c2w 'E'-toWord F    = c2w 'F'-toWord G    = c2w 'G'-toWord H    = c2w 'H'-toWord I    = c2w 'I'-toWord K    = c2w 'K'-toWord L    = c2w 'L'-toWord M    = c2w 'M'-toWord N    = c2w 'N'-toWord P    = c2w 'P'-toWord Q    = c2w 'Q'-toWord R    = c2w 'R'-toWord S    = c2w 'S'-toWord T    = c2w 'T'-toWord V    = c2w 'V'-toWord W    = c2w 'W'-toWord Y    = c2w 'Y'-toWord J    = c2w 'J'-toWord B    = c2w 'B'-toWord Z    = c2w 'Z'-toWord X    = c2w 'X'+toWord A = c2w 'A'+toWord C = c2w 'C'+toWord D = c2w 'D'+toWord E = c2w 'E'+toWord F = c2w 'F'+toWord G = c2w 'G'+toWord H = c2w 'H'+toWord I = c2w 'I'+toWord K = c2w 'K'+toWord L = c2w 'L'+toWord M = c2w 'M'+toWord N = c2w 'N'+toWord P = c2w 'P'+toWord Q = c2w 'Q'+toWord R = c2w 'R'+toWord S = c2w 'S'+toWord T = c2w 'T'+toWord V = c2w 'V'+toWord W = c2w 'W'+toWord Y = c2w 'Y'+toWord J = c2w 'J'+toWord B = c2w 'B'+toWord Z = c2w 'Z'+toWord X = c2w 'X' toWord Stop = c2w '*'-toWord Gap  = c2w '-'+toWord Gap = c2w '-'  fromWord :: Word8 -> AminoAcidI fromWord w = case w2c w of@@ -131,52 +157,56 @@   'B' -> B   'Z' -> Z   'X' -> X+  -- Question marks code for @X@s.+  '?' -> X   '*' -> Stop   '-' -> Gap+  -- Full stops code for gaps (@-@s).   '.' -> Gap-  _   -> error "fromWord: Cannot convert Word8 to AminoAcidI"+  _ -> error "fromWord: Cannot convert Word8 to AminoAcidI" -derivingUnbox "AminoAcidI"-    [t| AminoAcidI -> Word8 |]-    [| toWord |]-    [| fromWord |]+derivingUnbox+  "AminoAcidI"+  [t|AminoAcidI -> Word8|]+  [|toWord|]+  [|fromWord|]  instance C.Character AminoAcidI where-  toWord   = toWord+  toWord = toWord   fromWord = fromWord  instance C.CharacterX AminoAcidI where   gap = Gap  toStandard :: AminoAcidI -> [AminoAcidI]-toStandard A    = [A]-toStandard C    = [C]-toStandard D    = [D]-toStandard E    = [E]-toStandard F    = [F]-toStandard G    = [G]-toStandard H    = [H]-toStandard I    = [I]-toStandard K    = [K]-toStandard L    = [L]-toStandard M    = [M]-toStandard N    = [N]-toStandard P    = [P]-toStandard Q    = [Q]-toStandard R    = [R]-toStandard S    = [S]-toStandard T    = [T]-toStandard V    = [V]-toStandard W    = [W]-toStandard Y    = [Y]-toStandard J    = [L, I]-toStandard B    = [D, N]-toStandard Z    = [E, Q]-toStandard X    = [A, C, D, E, F, G, H, I, K, L, M, N, P, Q, R, S, T, V, W, Y]+toStandard A = [A]+toStandard C = [C]+toStandard D = [D]+toStandard E = [E]+toStandard F = [F]+toStandard G = [G]+toStandard H = [H]+toStandard I = [I]+toStandard K = [K]+toStandard L = [L]+toStandard M = [M]+toStandard N = [N]+toStandard P = [P]+toStandard Q = [Q]+toStandard R = [R]+toStandard S = [S]+toStandard T = [T]+toStandard V = [V]+toStandard W = [W]+toStandard Y = [Y]+toStandard J = [L, I]+toStandard B = [D, N]+toStandard Z = [E, Q]+toStandard X = [A, C, D, E, F, G, H, I, K, L, M, N, P, Q, R, S, T, V, W, Y] toStandard Stop = []-toStandard Gap  = []+toStandard Gap = []  instance C.CharacterI AminoAcidI where-  unknown    = X-  iupac      = [J, B, Z, X]+  unknown = X+  iupac = [J, B, Z, X]   toStandard = toStandard
src/ELynx/Data/Character/AminoAcidS.hs view
@@ -1,96 +1,111 @@ {-# LANGUAGE MultiParamTypeClasses #-}-{-# LANGUAGE TemplateHaskell       #-}-{-# LANGUAGE TypeFamilies          #-}--{- |-Module      :  ELynx.Data.AminoAcid-Description :  Amino acid related types and functions-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Thu Oct  4 18:26:35 2018.--See header of 'ELynx.Data.Alphabet.Alphabet'.--Amino acids with gaps and translation stops.--@-Amino Acid Code:  Three letter Code:  Amino Acid:-----------------  ------------------  ------------A                 Ala                 Alanine-C                 Cys                 Cysteine-D                 Asp                 Aspartic Acid-E                 Glu                 Glutamic Acid-F                 Phe                 Phenylalanine-G                 Gly                 Glycine-H                 His                 Histidine-I                 Ile                 Isoleucine-K                 Lys                 Lysine-L                 Leu                 Leucine-M                 Met                 Methionine-N                 Asn                 Asparagine-P                 Pro                 Proline-Q                 Gln                 Glutamine-R                 Arg                 Arginine-S                 Ser                 Serine-T                 Thr                 Threonine-V                 Val                 Valine-W                 Trp                 Tryptophan-Y                 Tyr                 Tyrosine-------------------*                 Stp                 No amino acid--------------------                 Gap                 No amino acid-.                 Gap                 No amino acid-@---}+{-# LANGUAGE TemplateHaskell #-}+{-# LANGUAGE TypeFamilies #-} +-- |+-- Module      :  ELynx.Data.AminoAcid+-- Description :  Amino acid related types and functions+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Thu Oct  4 18:26:35 2018.+--+-- See header of 'ELynx.Data.Alphabet.Alphabet'.+--+-- Amino acids with gaps and translation stops.+--+-- @+-- Amino Acid Code:  Three letter Code:  Amino Acid:+-- ----------------  ------------------  -----------+-- A                 Ala                 Alanine+-- C                 Cys                 Cysteine+-- D                 Asp                 Aspartic Acid+-- E                 Glu                 Glutamic Acid+-- F                 Phe                 Phenylalanine+-- G                 Gly                 Glycine+-- H                 His                 Histidine+-- I                 Ile                 Isoleucine+-- K                 Lys                 Lysine+-- L                 Leu                 Leucine+-- M                 Met                 Methionine+-- N                 Asn                 Asparagine+-- P                 Pro                 Proline+-- Q                 Gln                 Glutamine+-- R                 Arg                 Arginine+-- S                 Ser                 Serine+-- T                 Thr                 Threonine+-- V                 Val                 Valine+-- W                 Trp                 Tryptophan+-- Y                 Tyr                 Tyrosine+-- ----------------  ------------------  -----------+-- *                 Stp                 No amino acid+-- ----------------  ------------------  -----------+-- -                 Gap                 No amino acid (preferred)+-- .                 Gap                 No amino acid+-- @ module ELynx.Data.Character.AminoAcidS-  ( AminoAcidS(..)+  ( AminoAcidS (..),   ) where -import           Data.Vector.Unboxed.Deriving-import           Data.Word8--import qualified ELynx.Data.Character.Character-                                               as C-import           ELynx.Tools+import Data.Vector.Unboxed.Deriving+import Data.Word8+import qualified ELynx.Data.Character.Character as C+import ELynx.Tools  -- | Amino acids.-data AminoAcidS = A | C | D | E | F | G | H | I | K | L | M | N | P | Q | R | S | T | V | W | Y-                | Stop-                | Gap+data AminoAcidS+  = A+  | C+  | D+  | E+  | F+  | G+  | H+  | I+  | K+  | L+  | M+  | N+  | P+  | Q+  | R+  | S+  | T+  | V+  | W+  | Y+  | Stop+  | Gap   deriving (Show, Read, Eq, Ord, Enum, Bounded)  toWord :: AminoAcidS -> Word8-toWord A    = c2w 'A'-toWord C    = c2w 'C'-toWord D    = c2w 'D'-toWord E    = c2w 'E'-toWord F    = c2w 'F'-toWord G    = c2w 'G'-toWord H    = c2w 'H'-toWord I    = c2w 'I'-toWord K    = c2w 'K'-toWord L    = c2w 'L'-toWord M    = c2w 'M'-toWord N    = c2w 'N'-toWord P    = c2w 'P'-toWord Q    = c2w 'Q'-toWord R    = c2w 'R'-toWord S    = c2w 'S'-toWord T    = c2w 'T'-toWord V    = c2w 'V'-toWord W    = c2w 'W'-toWord Y    = c2w 'Y'+toWord A = c2w 'A'+toWord C = c2w 'C'+toWord D = c2w 'D'+toWord E = c2w 'E'+toWord F = c2w 'F'+toWord G = c2w 'G'+toWord H = c2w 'H'+toWord I = c2w 'I'+toWord K = c2w 'K'+toWord L = c2w 'L'+toWord M = c2w 'M'+toWord N = c2w 'N'+toWord P = c2w 'P'+toWord Q = c2w 'Q'+toWord R = c2w 'R'+toWord S = c2w 'S'+toWord T = c2w 'T'+toWord V = c2w 'V'+toWord W = c2w 'W'+toWord Y = c2w 'Y' toWord Stop = c2w '*'-toWord Gap  = c2w '-'+toWord Gap = c2w '-'  fromWord :: Word8 -> AminoAcidS fromWord w = case w2c w of@@ -117,15 +132,16 @@   '*' -> Stop   '-' -> Gap   '.' -> Gap-  _   -> error "fromWord: Cannot convert to AminoAcidS."+  _ -> error "fromWord: Cannot convert to AminoAcidS." -derivingUnbox "AminoAcidS"-    [t| AminoAcidS -> Word8 |]-    [| toWord |]-    [| fromWord |]+derivingUnbox+  "AminoAcidS"+  [t|AminoAcidS -> Word8|]+  [|toWord|]+  [|fromWord|]  instance C.Character AminoAcidS where-  toWord   = toWord+  toWord = toWord   fromWord = fromWord  instance C.CharacterX AminoAcidS where
src/ELynx/Data/Character/AminoAcidX.hs view
@@ -1,93 +1,108 @@ {-# LANGUAGE MultiParamTypeClasses #-}-{-# LANGUAGE TemplateHaskell       #-}-{-# LANGUAGE TypeFamilies          #-}--{- |-Module      :  ELynx.Data.AminoAcid-Description :  Amino acid related types and functions-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Thu Oct  4 18:26:35 2018.--See header of 'ELynx.Data.Alphabet.Alphabet'.--Extended amino acid with gaps. See also-https://www.bioinformatics.org/sms/iupac.html or-https://en.wikipedia.org/wiki/International_Union_of_Pure_and_Applied_Chemistry.--@-Amino Acid Code:  Three letter Code:  Amino Acid:-----------------  ------------------  ------------A                 Ala                 Alanine-C                 Cys                 Cysteine-D                 Asp                 Aspartic Acid-E                 Glu                 Glutamic Acid-F                 Phe                 Phenylalanine-G                 Gly                 Glycine-H                 His                 Histidine-I                 Ile                 Isoleucine-K                 Lys                 Lysine-L                 Leu                 Leucine-M                 Met                 Methionine-N                 Asn                 Asparagine-P                 Pro                 Proline-Q                 Gln                 Glutamine-R                 Arg                 Arginine-S                 Ser                 Serine-T                 Thr                 Threonine-V                 Val                 Valine-W                 Trp                 Tryptophan-Y                 Tyr                 Tyrosine--------------------                 Gap                 No amino acid-.                 Gap                 No amino acid-@---}+{-# LANGUAGE TemplateHaskell #-}+{-# LANGUAGE TypeFamilies #-} +-- |+-- Module      :  ELynx.Data.AminoAcid+-- Description :  Amino acid related types and functions+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Thu Oct  4 18:26:35 2018.+--+-- See header of 'ELynx.Data.Alphabet.Alphabet'.+--+-- Extended amino acid with gaps. See also+-- https://www.bioinformatics.org/sms/iupac.html or+-- https://en.wikipedia.org/wiki/International_Union_of_Pure_and_Applied_Chemistry.+--+-- @+-- Amino Acid Code:  Three letter Code:  Amino Acid:+-- ----------------  ------------------  -----------+-- A                 Ala                 Alanine+-- C                 Cys                 Cysteine+-- D                 Asp                 Aspartic Acid+-- E                 Glu                 Glutamic Acid+-- F                 Phe                 Phenylalanine+-- G                 Gly                 Glycine+-- H                 His                 Histidine+-- I                 Ile                 Isoleucine+-- K                 Lys                 Lysine+-- L                 Leu                 Leucine+-- M                 Met                 Methionine+-- N                 Asn                 Asparagine+-- P                 Pro                 Proline+-- Q                 Gln                 Glutamine+-- R                 Arg                 Arginine+-- S                 Ser                 Serine+-- T                 Thr                 Threonine+-- V                 Val                 Valine+-- W                 Trp                 Tryptophan+-- Y                 Tyr                 Tyrosine+-- ----------------  ------------------  -----------+-- -                 Gap                 No amino acid+-- .                 Gap                 No amino acid+-- @ module ELynx.Data.Character.AminoAcidX-  ( AminoAcidX(..)+  ( AminoAcidX (..),   ) where -import           Data.Vector.Unboxed.Deriving-import           Data.Word8--import qualified ELynx.Data.Character.Character-                                               as C-import           ELynx.Tools+import Data.Vector.Unboxed.Deriving+import Data.Word8+import qualified ELynx.Data.Character.Character as C+import ELynx.Tools  -- | Amino acids.-data AminoAcidX = A | C | D | E | F | G | H | I | K | L | M | N | P | Q | R | S | T | V | W | Y-                | Gap+data AminoAcidX+  = A+  | C+  | D+  | E+  | F+  | G+  | H+  | I+  | K+  | L+  | M+  | N+  | P+  | Q+  | R+  | S+  | T+  | V+  | W+  | Y+  | Gap   deriving (Show, Read, Eq, Ord, Enum, Bounded)  toWord :: AminoAcidX -> Word8-toWord A   = c2w 'A'-toWord C   = c2w 'C'-toWord D   = c2w 'D'-toWord E   = c2w 'E'-toWord F   = c2w 'F'-toWord G   = c2w 'G'-toWord H   = c2w 'H'-toWord I   = c2w 'I'-toWord K   = c2w 'K'-toWord L   = c2w 'L'-toWord M   = c2w 'M'-toWord N   = c2w 'N'-toWord P   = c2w 'P'-toWord Q   = c2w 'Q'-toWord R   = c2w 'R'-toWord S   = c2w 'S'-toWord T   = c2w 'T'-toWord V   = c2w 'V'-toWord W   = c2w 'W'-toWord Y   = c2w 'Y'+toWord A = c2w 'A'+toWord C = c2w 'C'+toWord D = c2w 'D'+toWord E = c2w 'E'+toWord F = c2w 'F'+toWord G = c2w 'G'+toWord H = c2w 'H'+toWord I = c2w 'I'+toWord K = c2w 'K'+toWord L = c2w 'L'+toWord M = c2w 'M'+toWord N = c2w 'N'+toWord P = c2w 'P'+toWord Q = c2w 'Q'+toWord R = c2w 'R'+toWord S = c2w 'S'+toWord T = c2w 'T'+toWord V = c2w 'V'+toWord W = c2w 'W'+toWord Y = c2w 'Y' toWord Gap = c2w '-'  fromWord :: Word8 -> AminoAcidX@@ -114,15 +129,16 @@   'Y' -> Y   '-' -> Gap   '.' -> Gap-  _   -> error "fromWord: Cannot convert to AminoAcidX."+  _ -> error "fromWord: Cannot convert to AminoAcidX." -derivingUnbox "AminoAcidX"-    [t| AminoAcidX -> Word8 |]-    [| toWord |]-    [| fromWord |]+derivingUnbox+  "AminoAcidX"+  [t|AminoAcidX -> Word8|]+  [|toWord|]+  [|fromWord|]  instance C.Character AminoAcidX where-  toWord   = toWord+  toWord = toWord   fromWord = fromWord  instance C.CharacterX AminoAcidX where
src/ELynx/Data/Character/Character.hs view
@@ -1,48 +1,46 @@-{- |-Module      :  Character-Description :  Character interface-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Fri Oct 12 16:24:02 2018.--See header of 'ELynx.Data.Alphabet.Alphabet'.---}-+-- |+-- Module      :  Character+-- Description :  Character interface+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Fri Oct 12 16:24:02 2018.+--+-- See header of 'ELynx.Data.Alphabet.Alphabet'. module ELynx.Data.Character.Character-  ( Character(..)-  , fromChar-  , toChar-  , fromString-  , toString-  , CharacterX(..)-  , isGap-  , CharacterI(..)-  , isUnknown-  , isIUPAC-  , isStandard-  , convert+  ( Character (..),+    fromChar,+    toChar,+    fromString,+    toString,+    CharacterX (..),+    isGap,+    CharacterI (..),+    isUnknown,+    isIUPAC,+    isStandard,+    convert,   ) where -import qualified Data.Set                      as S-import           Data.Vector.Unboxed.Base       ( Unbox )-import           Data.Word8                     ( Word8 )--import           ELynx.Tools+import qualified Data.Set as S+import Data.Vector.Unboxed.Base (Unbox)+import Data.Word8 (Word8)+import ELynx.Tools  -- XXX: Remove name clash with ELynx.Data.Alphabet.Alphabet.Character?+ -- | A set of characters forms an 'ELynx.Data.Alphabet.Alphabet'. At the -- moment, 'Word8' is used, since none of the alphabets has more than 255 -- characters. class (Show a, Read a, Eq a, Ord a, Enum a, Bounded a, Unbox a) => Character a where   -- | Write characters.-  toWord   :: a -> Word8+  toWord :: a -> Word8+   -- | Read characters.   fromWord :: Word8 -> a @@ -64,7 +62,7 @@  -- | An extended character type with gaps and unknowns. class Character a => CharacterX a where-  gap     :: a+  gap :: a  -- | Is the character a gap or unknown? isGap :: CharacterX a => a -> Bool@@ -72,8 +70,8 @@  -- | IUPAC characters with a mapping to extended characters. class CharacterX a => CharacterI a where-  unknown    :: a-  iupac      :: [a]+  unknown :: a+  iupac :: [a]   toStandard :: a -> [a]  -- | Check if a IUPAC 'CharacterI' is unknown (e.g., N for nucleotides).
src/ELynx/Data/Character/Codon.hs view
@@ -1,53 +1,45 @@ {-# LANGUAGE DeriveGeneric #-} -{- |-Module      :  ELynx.Data.Character.Codon-Description :  Codons are triplets of nucleotides-Copyright   :  (c) Dominik Schrempf 2020-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Thu May 16 07:58:50 2019.--The different universal codes.-- https://www.ncbi.nlm.nih.gov/Taxonomy/Utils/wprintgc.cgi?mode=c-- http://www.bioinformatics.org/sms2/genetic_code.html-- https://en.wikipedia.org/wiki/Genetic_code---}-+-- |+-- Module      :  ELynx.Data.Character.Codon+-- Description :  Codons are triplets of nucleotides+-- Copyright   :  (c) Dominik Schrempf 2020+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Thu May 16 07:58:50 2019.+--+-- The different universal codes.+-- - https://www.ncbi.nlm.nih.gov/Taxonomy/Utils/wprintgc.cgi?mode=c+-- - http://www.bioinformatics.org/sms2/genetic_code.html+-- - https://en.wikipedia.org/wiki/Genetic_code module ELynx.Data.Character.Codon-  ( Codon(Codon)-  , unsafeFromVec-  , UniversalCode(..)-  , translate-  , translateX-  , translateI+  ( Codon (Codon),+    unsafeFromVec,+    UniversalCode (..),+    translate,+    translateX,+    translateI,   ) where -import           Data.Aeson                     ( FromJSON-                                                , ToJSON-                                                )-import           Data.List-import           GHC.Generics                   ( Generic )-import qualified Data.Map                      as M-import qualified Data.Vector.Generic           as V--import qualified ELynx.Data.Character.AminoAcidI-                                               as AI-import           ELynx.Data.Character.AminoAcidS-import qualified ELynx.Data.Character.Character-                                               as C-import qualified ELynx.Data.Character.Nucleotide-                                               as N-import qualified ELynx.Data.Character.NucleotideI-                                               as NI-import qualified ELynx.Data.Character.NucleotideX-                                               as NX+import Data.Aeson+  ( FromJSON,+    ToJSON,+  )+import Data.List+import qualified Data.Map as M+import qualified Data.Vector.Generic as V+import qualified ELynx.Data.Character.AminoAcidI as AI+import ELynx.Data.Character.AminoAcidS+import qualified ELynx.Data.Character.Character as C+import qualified ELynx.Data.Character.Nucleotide as N+import qualified ELynx.Data.Character.NucleotideI as NI+import qualified ELynx.Data.Character.NucleotideX as NX+import GHC.Generics (Generic)  -- | Codons are triplets of characters. newtype Codon a = Codon (a, a, a)@@ -76,155 +68,158 @@   M.fromList $ zipWith4 (\f s t a -> (Codon (f, s, t), a)) xs ys zs as  nucs :: Enum a => [a]-nucs = map toEnum [3, 1, 0, 2]     -- Order T, C, A , G.+nucs = map toEnum [3, 1, 0, 2] -- Order T, C, A , G.  -- Permutation of the triplets PLUS GAPS! I avoid 'Z' because I do not want to -- translate DNAI. base1, base2, base3 :: Enum a => [a]-base1 = [ n | n <- nucs, _ <- [0 .. 3 :: Int], _ <- [0 .. 3 :: Int] ]+base1 = [n | n <- nucs, _ <- [0 .. 3 :: Int], _ <- [0 .. 3 :: Int]] -- base1 = "TTTTTTTTTTTTTTTTCCCCCCCCCCCCCCCCAAAAAAAAAAAAAAAAGGGGGGGGGGGGGGGG" ++ "-."-base2 = [ n | _ <- [0 .. 3 :: Int], n <- nucs, _ <- [0 .. 3 :: Int] ]+base2 = [n | _ <- [0 .. 3 :: Int], n <- nucs, _ <- [0 .. 3 :: Int]] -- base2 = "TTTTCCCCAAAAGGGGTTTTCCCCAAAAGGGGTTTTCCCCAAAAGGGGTTTTCCCCAAAAGGGG" ++ "-."-base3 = [ n | _ <- [0 .. 3 :: Int], _ <- [0 .. 3 :: Int], n <- nucs ]+base3 = [n | _ <- [0 .. 3 :: Int], _ <- [0 .. 3 :: Int], n <- nucs]+ -- base3 = "TCAGTCAGTCAGTCAGTCAGTCAGTCAGTCAGTCAGTCAGTCAGTCAGTCAGTCAGTCAGTCAG" ++ "-."  -- The actual codes. standard :: [AminoAcidS] standard =-  [ F-  , F-  , L-  , L-  , S-  , S-  , S-  , S-  , Y-  , Y-  , Stop-  , Stop-  , C-  , C-  , Stop-  , W-  , L-  , L-  , L-  , L-  , P-  , P-  , P-  , P-  , H-  , H-  , Q-  , Q-  , R-  , R-  , R-  , R-  , I-  , I-  , I-  , M-  , T-  , T-  , T-  , T-  , N-  , N-  , K-  , K-  , S-  , S-  , R-  , R-  , V-  , V-  , V-  , V-  , A-  , A-  , A-  , A-  , D-  , D-  , E-  , E-  , G-  , G-  , G-  , G+  [ F,+    F,+    L,+    L,+    S,+    S,+    S,+    S,+    Y,+    Y,+    Stop,+    Stop,+    C,+    C,+    Stop,+    W,+    L,+    L,+    L,+    L,+    P,+    P,+    P,+    P,+    H,+    H,+    Q,+    Q,+    R,+    R,+    R,+    R,+    I,+    I,+    I,+    M,+    T,+    T,+    T,+    T,+    N,+    N,+    K,+    K,+    S,+    S,+    R,+    R,+    V,+    V,+    V,+    V,+    A,+    A,+    A,+    A,+    D,+    D,+    E,+    E,+    G,+    G,+    G,+    G   ]+ -- "FFLLSSSSYY**CC*WLLLLPPPPHHQQRRRRIIIMTTTTNNKKSSRRVVVVAAAADDEEGGGG" ++ "--"  vertebrateMitochondrial :: [AminoAcidS] vertebrateMitochondrial =-  [ F-  , F-  , L-  , L-  , S-  , S-  , S-  , S-  , Y-  , Y-  , Stop-  , Stop-  , C-  , C-  , W-  , W-  , L-  , L-  , L-  , L-  , P-  , P-  , P-  , P-  , H-  , H-  , Q-  , Q-  , R-  , R-  , R-  , R-  , I-  , I-  , M-  , M-  , T-  , T-  , T-  , T-  , N-  , N-  , K-  , K-  , S-  , S-  , Stop-  , Stop-  , V-  , V-  , V-  , V-  , A-  , A-  , A-  , A-  , D-  , D-  , E-  , E-  , G-  , G-  , G-  , G+  [ F,+    F,+    L,+    L,+    S,+    S,+    S,+    S,+    Y,+    Y,+    Stop,+    Stop,+    C,+    C,+    W,+    W,+    L,+    L,+    L,+    L,+    P,+    P,+    P,+    P,+    H,+    H,+    Q,+    Q,+    R,+    R,+    R,+    R,+    I,+    I,+    M,+    M,+    T,+    T,+    T,+    T,+    N,+    N,+    K,+    K,+    S,+    S,+    Stop,+    Stop,+    V,+    V,+    V,+    V,+    A,+    A,+    A,+    A,+    D,+    D,+    E,+    E,+    G,+    G,+    G,+    G   ]+ -- "FFLLSSSSYY**CCWWLLLLPPPPHHQQRRRRIIMMTTTTNNKKSS**VVVVAAAADDEEGGGG" ++ "--"  -- | Translate a codon to amino acids including translation stops.@@ -249,6 +244,7 @@ translateI code codon@(Codon (x, y, z))   | C.isIUPAC x || C.isIUPAC y || C.isIUPAC z = AI.X   | otherwise = C.convert . translateX code . convert $ codon+ -- translateI :: UniversalCode -> Codon NI.NucleotideI -> AI.AminoAcidI -- translateI _ (Codon (NI.N, _,    _   )) = AI.X -- translateI _ (Codon (_   , NI.N, _   )) = AI.X
src/ELynx/Data/Character/Nucleotide.hs view
@@ -1,43 +1,38 @@ {-# LANGUAGE MultiParamTypeClasses #-}-{-# LANGUAGE TemplateHaskell       #-}-{-# LANGUAGE TypeFamilies          #-}--{- |-Module      :  ELynx.Data.Nucleotide-Description :  Nucleotides-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Thu Oct  4 18:26:35 2018.--See header of 'ELynx.Data.Alphabet.Alphabet'.--@-Symbol  Description  Bases represented  Complement-------  -----------  -----------------  -----------A       Adenine      A                  T-C       Cytosine        C               G-G       Guanine            G            C-T       Thymine               T         A-@---}+{-# LANGUAGE TemplateHaskell #-}+{-# LANGUAGE TypeFamilies #-} +-- |+-- Module      :  ELynx.Data.Nucleotide+-- Description :  Nucleotides+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Thu Oct  4 18:26:35 2018.+--+-- See header of 'ELynx.Data.Alphabet.Alphabet'.+--+-- @+-- Symbol  Description  Bases represented  Complement+-- ------  -----------  -----------------  ----------+-- A       Adenine      A                  T+-- C       Cytosine        C               G+-- G       Guanine            G            C+-- T       Thymine               T         A+-- @ module ELynx.Data.Character.Nucleotide-  ( Nucleotide(..)+  ( Nucleotide (..),   ) where -import           Data.Vector.Unboxed.Deriving-import           Data.Word8--import qualified ELynx.Data.Character.Character-                                               as C-import           ELynx.Tools+import Data.Vector.Unboxed.Deriving+import Data.Word8+import qualified ELynx.Data.Character.Character as C+import ELynx.Tools  -- | Nucleotides. data Nucleotide = A | C | G | T@@ -59,13 +54,14 @@   'C' -> C   'G' -> G   'T' -> T-  c   -> error $ "fromWord: Cannot convert " ++ show c ++ " to Nucleotide."+  c -> error $ "fromWord: Cannot convert " ++ show c ++ " to Nucleotide." -derivingUnbox "Nucleotide"-    [t| Nucleotide -> Word8 |]-    [| toWord |]-    [| fromWord |]+derivingUnbox+  "Nucleotide"+  [t|Nucleotide -> Word8|]+  [|toWord|]+  [|fromWord|]  instance C.Character Nucleotide where-  toWord   = toWord+  toWord = toWord   fromWord = fromWord
src/ELynx/Data/Character/NucleotideI.hs view
@@ -1,69 +1,87 @@ {-# LANGUAGE MultiParamTypeClasses #-}-{-# LANGUAGE TemplateHaskell       #-}-{-# LANGUAGE TypeFamilies          #-}--{- |-Module      :  ELynx.Data.NucleotideI-Description :  Nucleotides with IUPAC characters-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Thu Oct  4 18:26:35 2018.---See header of 'ELynx.Data.Alphabet.Alphabet'.--Nucleotide IUPAC code. See also https://www.bioinformatics.org/sms/iupac.html or-https://en.wikipedia.org/wiki/International_Union_of_Pure_and_Applied_Chemistry.--@-Symbol  Description  Bases represented  Complement-------  -----------  -----------------  -----------A       Adenine      A                  T-C       Cytosine        C               G-G       Guanine            G            C-T       Thymine               T         A-------  -----------  -----------------  -----------U       Uracil                U         A-W       Weak         A        T         W-S       Strong          C  G            S-M       aMino        A  C               K-K       Keto               G  T         M-R       puRine       A     G            Y-Y       pYrimidine      C     T         R-B       not A           C  G  T         V-D       not C        A     G  T         H-H       not G        A  C     T         D-V       not T        A  C  G            B-------  -----------  -----------------  -----------N       any          A  C  G  T         N-------  -----------  -----------------  ------------ or .  Gap (Zero)                      --@---}+{-# LANGUAGE TemplateHaskell #-}+{-# LANGUAGE TypeFamilies #-} +-- |+-- Module      :  ELynx.Data.NucleotideI+-- Description :  Nucleotides with IUPAC characters+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Thu Oct  4 18:26:35 2018.+--+-- See header of 'ELynx.Data.Alphabet.Alphabet'.+--+-- Nucleotide IUPAC code. See also https://www.bioinformatics.org/sms/iupac.html or+-- https://en.wikipedia.org/wiki/International_Union_of_Pure_and_Applied_Chemistry.+--+-- Remarks:+--+-- - Question marks (@?@) are interpreted as unknowns (same as @N@). However, when+--   a sequence is printed/exported, @N@s will be used.+--+-- - Full stops (@.@) are interpreted as gaps (same as @-@). However, when a+--   sequence is printed/exported, @-@s will be used+--+-- @+-- Symbol  Description  Bases represented  Complement+-- ------  -----------  -----------------  ----------+-- A       Adenine      A                  T+-- C       Cytosine        C               G+-- G       Guanine            G            C+-- T       Thymine               T         A+-- ------  -----------  -----------------  ----------+-- U       Uracil                U         A+-- W       Weak         A        T         W+-- S       Strong          C  G            S+-- M       aMino        A  C               K+-- K       Keto               G  T         M+-- R       puRine       A     G            Y+-- Y       pYrimidine      C     T         R+-- B       not A           C  G  T         V+-- D       not C        A     G  T         H+-- H       not G        A  C     T         D+-- V       not T        A  C  G            B+-- ------  -----------  -----------------  ----------+-- N       any          A  C  G  T         N           (preferred)+-- ?       any          A  C  G  T         N+-- ------  -----------  -----------------  ----------+-- -       Gap (Zero)                      -           (preferred)+-- .       Gap (Zero)                      -+-- @ module ELynx.Data.Character.NucleotideI-  ( NucleotideI(..)+  ( NucleotideI (..),   ) where -import           Data.Vector.Unboxed.Deriving-import           Data.Word8--import qualified ELynx.Data.Character.Character-                                               as C-import           ELynx.Tools+import Data.Vector.Unboxed.Deriving+import Data.Word8+import qualified ELynx.Data.Character.Character as C+import ELynx.Tools  -- | NucleotideIs.-data NucleotideI = A | C | G | T-                 | U | W | S | M | K | R | Y | B | D | H | V-                 | N-                 | Gap+data NucleotideI+  = A+  | C+  | G+  | T+  | U+  | W+  | S+  | M+  | K+  | R+  | Y+  | B+  | D+  | H+  | V+  | N+  | Gap   deriving (Show, Read, Eq, Ord, Enum, Bounded)  -- See https://stackoverflow.com/a/31527024; apparently, pattern matching (and@@ -71,22 +89,22 @@ -- they are faster than guards (because equality has to be checked), and faster -- than lookups with sets. toWord :: NucleotideI -> Word8-toWord A   = c2w 'A'-toWord C   = c2w 'C'-toWord G   = c2w 'G'-toWord T   = c2w 'T'-toWord U   = c2w 'U'-toWord W   = c2w 'W'-toWord S   = c2w 'S'-toWord M   = c2w 'M'-toWord K   = c2w 'K'-toWord R   = c2w 'R'-toWord Y   = c2w 'Y'-toWord B   = c2w 'B'-toWord D   = c2w 'D'-toWord H   = c2w 'H'-toWord V   = c2w 'V'-toWord N   = c2w 'N'+toWord A = c2w 'A'+toWord C = c2w 'C'+toWord G = c2w 'G'+toWord T = c2w 'T'+toWord U = c2w 'U'+toWord W = c2w 'W'+toWord S = c2w 'S'+toWord M = c2w 'M'+toWord K = c2w 'K'+toWord R = c2w 'R'+toWord Y = c2w 'Y'+toWord B = c2w 'B'+toWord D = c2w 'D'+toWord H = c2w 'H'+toWord V = c2w 'V'+toWord N = c2w 'N' toWord Gap = c2w '-'  fromWord :: Word8 -> NucleotideI@@ -107,42 +125,44 @@   'H' -> H   'V' -> V   'N' -> N+  '?' -> N   '-' -> Gap   '.' -> Gap-  _   -> error "fromWord: Cannot convert to NucleotideI."+  _ -> error "fromWord: Cannot convert to NucleotideI." -derivingUnbox "NucleotideI"-    [t| NucleotideI -> Word8 |]-    [| toWord |]-    [| fromWord |]+derivingUnbox+  "NucleotideI"+  [t|NucleotideI -> Word8|]+  [|toWord|]+  [|fromWord|]  instance C.Character NucleotideI where-  toWord   = toWord+  toWord = toWord   fromWord = fromWord  toStandard :: NucleotideI -> [NucleotideI]-toStandard A   = [A]-toStandard C   = [C]-toStandard G   = [G]-toStandard T   = [T]-toStandard U   = [T]-toStandard W   = [A, T]-toStandard S   = [G, C]-toStandard M   = [A, C]-toStandard K   = [G, T]-toStandard R   = [A, G]-toStandard Y   = [C, T]-toStandard B   = [C, G, T]-toStandard D   = [A, G, T]-toStandard H   = [A, C, T]-toStandard V   = [A, C, G]-toStandard N   = [A, C, G, T]+toStandard A = [A]+toStandard C = [C]+toStandard G = [G]+toStandard T = [T]+toStandard U = [T]+toStandard W = [A, T]+toStandard S = [G, C]+toStandard M = [A, C]+toStandard K = [G, T]+toStandard R = [A, G]+toStandard Y = [C, T]+toStandard B = [C, G, T]+toStandard D = [A, G, T]+toStandard H = [A, C, T]+toStandard V = [A, C, G]+toStandard N = [A, C, G, T] toStandard Gap = []  instance C.CharacterX NucleotideI where   gap = Gap  instance C.CharacterI NucleotideI where-  unknown    = N-  iupac      = [U, W, S, M, K, R, Y, B, D, H, V, N]+  unknown = N+  iupac = [U, W, S, M, K, R, Y, B, D, H, V, N]   toStandard = toStandard
src/ELynx/Data/Character/NucleotideX.hs view
@@ -1,60 +1,58 @@ {-# LANGUAGE MultiParamTypeClasses #-}-{-# LANGUAGE TemplateHaskell       #-}-{-# LANGUAGE TypeFamilies          #-}--{- |-Module      :  ELynx.Data.NucleotideX-Description :  Extended nucleotides including gaps and unknowns-Copyright   :  (c) Dominik Schrempf 2018--License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--See header of 'ELynx.Data.Alphabet'.--Extended nucleotides with gaps. See also-https://www.bioinformatics.org/sms/iupac.html or-https://en.wikipedia.org/wiki/International_Union_of_Pure_and_Applied_Chemistry.--@-Symbol  Description  Bases represented  Complement-------  -----------  -----------------  -----------A       Adenine      A                  T-C       Cytosine        C               G-G       Guanine            G            C-T       Thymine               T         A-------  -----------  -----------------  ------------ or .  Gap (Zero)                      --@----}+{-# LANGUAGE TemplateHaskell #-}+{-# LANGUAGE TypeFamilies #-} +-- |+-- Module      :  ELynx.Data.NucleotideX+-- Description :  Extended nucleotides including gaps and unknowns+-- Copyright   :  (c) Dominik Schrempf 2018+--+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- See header of 'ELynx.Data.Alphabet'.+--+-- Extended nucleotides with gaps. See also+-- https://www.bioinformatics.org/sms/iupac.html or+-- https://en.wikipedia.org/wiki/International_Union_of_Pure_and_Applied_Chemistry.+--+-- @+-- Symbol  Description  Bases represented  Complement+-- ------  -----------  -----------------  ----------+-- A       Adenine      A                  T+-- C       Cytosine        C               G+-- G       Guanine            G            C+-- T       Thymine               T         A+-- ------  -----------  -----------------  ----------+-- - or .  Gap (Zero)                      -+-- @ module ELynx.Data.Character.NucleotideX-  ( NucleotideX(..)+  ( NucleotideX (..),   ) where -import           Data.Vector.Unboxed.Deriving-import           Data.Word8--import qualified ELynx.Data.Character.Character-                                               as C-import           ELynx.Tools+import Data.Vector.Unboxed.Deriving+import Data.Word8+import qualified ELynx.Data.Character.Character as C+import ELynx.Tools  -- | Extended nucleotides.-data NucleotideX = A | C | G | T-                 | Gap+data NucleotideX+  = A+  | C+  | G+  | T+  | Gap   deriving (Show, Read, Eq, Ord, Enum, Bounded)  toWord :: NucleotideX -> Word8-toWord A   = c2w 'A'-toWord C   = c2w 'C'-toWord G   = c2w 'G'-toWord T   = c2w 'T'+toWord A = c2w 'A'+toWord C = c2w 'C'+toWord G = c2w 'G'+toWord T = c2w 'T' toWord Gap = c2w '-'  fromWord :: Word8 -> NucleotideX@@ -65,15 +63,16 @@   'T' -> T   '-' -> Gap   '.' -> Gap-  c   -> error $ "fromWord: Cannot convert " ++ show c ++ " to NucleotideX."+  c -> error $ "fromWord: Cannot convert " ++ show c ++ " to NucleotideX." -derivingUnbox "NucleotideX"-    [t| NucleotideX -> Word8 |]-    [| toWord |]-    [| fromWord |]+derivingUnbox+  "NucleotideX"+  [t|NucleotideX -> Word8|]+  [|toWord|]+  [|fromWord|]  instance C.Character NucleotideX where-  toWord   = toWord+  toWord = toWord   fromWord = fromWord  instance C.CharacterX NucleotideX where
src/ELynx/Data/Sequence/Alignment.hs view
@@ -1,79 +1,75 @@-{- |-Module      :  ELynx.Data.Sequence.Alignment-Description :  Multi sequence alignment related types and functions-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable--Portability :  portable--Creation date: Thu Oct  4 18:40:18 2018.--This module is to be imported qualified.---}--+-- |+-- Module      :  ELynx.Data.Sequence.Alignment+-- Description :  Multi sequence alignment related types and functions+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+--+-- Portability :  portable+--+-- Creation date: Thu Oct  4 18:40:18 2018.+--+-- This module is to be imported qualified. module ELynx.Data.Sequence.Alignment-  ( Alignment(..)-  , length-  , nSequences-  -- | * Input, output-  , fromSequences-  , toSequences-  , summarize-  -- | * Manipulation-  , join-  , concat-  , concatAlignments-  , filterColsOnlyStd-  , filterColsStd-  , filterColsNoGaps-  -- | * Analysis-  , FrequencyData-  , distribution-  , toFrequencyData-  , kEffEntropy-  , kEffHomoplasy-  , countIUPACChars-  , countGaps-  , countUnknowns-  -- | * Sub sample-  , subSample-  , randomSubSample+  ( Alignment (..),+    length,+    nSequences,+    -- | * Input, output+    fromSequences,+    toSequences,+    summarize,+    -- | * Manipulation+    join,+    concat,+    concatAlignments,+    filterColsOnlyStd,+    filterColsStd,+    filterColsNoGaps,+    -- | * Analysis+    FrequencyData,+    distribution,+    toFrequencyData,+    kEffEntropy,+    kEffHomoplasy,+    countIUPACChars,+    countGaps,+    countUnknowns,+    -- | * Sub sample+    subSample,+    randomSubSample,   ) where -import           Control.Monad           hiding ( join )-import           Control.Monad.Primitive-import qualified Data.ByteString.Lazy.Char8    as L-import           Data.List               hiding ( concat-                                                , length-                                                )-import qualified Data.Matrix.Unboxed           as M-import qualified Data.Vector.Unboxed           as V-import           Prelude                 hiding ( concat-                                                , length-                                                )-import           System.Random.MWC--import qualified ELynx.Data.Alphabet.Alphabet  as A-import           ELynx.Data.Alphabet.Character-import qualified ELynx.Data.Alphabet.DistributionDiversity-                                               as D-import           ELynx.Data.Sequence.Defaults-import qualified ELynx.Data.Sequence.Sequence  as S-import           ELynx.Tools+import Control.Monad hiding (join)+import Control.Monad.Primitive+import qualified Data.ByteString.Lazy.Char8 as L+import Data.List hiding+  ( concat,+    length,+  )+import qualified Data.Matrix.Unboxed as M+import qualified Data.Vector.Unboxed as V+import qualified ELynx.Data.Alphabet.Alphabet as A+import ELynx.Data.Alphabet.Character+import qualified ELynx.Data.Alphabet.DistributionDiversity as D+import ELynx.Data.Sequence.Defaults+import qualified ELynx.Data.Sequence.Sequence as S+import ELynx.Tools+import System.Random.MWC+import Prelude hiding+  ( concat,+    length,+  )  -- | A collection of sequences. data Alignment = Alignment-                              { names        :: [S.Name]-                              , descriptions :: [S.Description]-                              , alphabet     :: A.Alphabet-                              , matrix       :: M.Matrix Character-                              }+  { names :: [S.Name],+    descriptions :: [S.Description],+    alphabet :: A.Alphabet,+    matrix :: M.Matrix Character+  }   deriving (Show, Eq)  -- | Number of sites.@@ -87,24 +83,28 @@ -- | Create 'Alignment' from a list of 'S.Sequence's. fromSequences :: [S.Sequence] -> Either String Alignment fromSequences ss-  | S.equalLength ss && allEqual (map S.alphabet ss) = Right-  $ Alignment ns ds a d+  | S.equalLength ss && allEqual (map S.alphabet ss) =+    Right $+      Alignment ns ds a d   | S.equalLength ss = Left "Sequences do not have equal codes."   | otherwise = Left "Sequences do not have equal lengths."- where-  ns  = map S.name ss-  ds  = map S.description ss-  a   = S.alphabet $ head ss-  bss = map S.characters ss-  d   = M.fromRows bss+  where+    ns = map S.name ss+    ds = map S.description ss+    a = S.alphabet $ head ss+    bss = map S.characters ss+    d = M.fromRows bss  -- | Conversion to list of 'S.Sequence's. toSequences :: Alignment -> [S.Sequence]-toSequences (Alignment ns ds a da) = zipWith3 (\n d r -> S.Sequence n d a r)-                                              ns-                                              ds-                                              rows-  where rows = M.toRows da+toSequences (Alignment ns ds a da) =+  zipWith3+    (\n d r -> S.Sequence n d a r)+    ns+    ds+    rows+  where+    rows = M.toRows da  -- -- | Show a 'Alignment', untrimmed. -- summarizeSeq :: Alignment -> Int -> L.ByteString@@ -115,29 +115,29 @@  header :: Alignment -> L.ByteString header a =-  L.unlines-    $  [ L.pack "Multi sequence alignment."-       , L.pack $ "Code: " ++ A.alphabetDescription (alphabet a) ++ "."-       , L.pack $ "Length: " ++ show (length a) ++ "."-       ]-    ++ reportLengthSummary-    ++ reportNumberSummary- where-  reportLengthSummary =-    [ L.pack-        $  "For each sequence, the "-        ++ show summaryLength-        ++ " first bases are shown."-    | length a > summaryLength-    ]-  reportNumberSummary =-    [ L.pack-        $  show summaryNSequences-        ++ " out of "-        ++ show (nSequences a)-        ++ " sequences are shown."-    | nSequences a > summaryNSequences+  L.unlines $+    [ L.pack "Multi sequence alignment.",+      L.pack $ "Code: " ++ A.alphabetDescription (alphabet a) ++ ".",+      L.pack $ "Length: " ++ show (length a) ++ "."     ]+      ++ reportLengthSummary+      ++ reportNumberSummary+  where+    reportLengthSummary =+      [ L.pack $+          "For each sequence, the "+            ++ show summaryLength+            ++ " first bases are shown."+        | length a > summaryLength+      ]+    reportNumberSummary =+      [ L.pack $+          show summaryNSequences+            ++ " out of "+            ++ show (nSequences a)+            ++ " sequences are shown."+        | nSequences a > summaryNSequences+      ]  -- | Similar to 'S.summarizeSequenceList' but with different Header. summarize :: Alignment -> L.ByteString@@ -148,49 +148,52 @@ join :: Alignment -> Alignment -> Alignment -- top bottom. join t b-  | length t /= length b = error-    "join: Multi sequence alignments do not have equal lengths."-  | alphabet t /= alphabet b = error-    "join: Multi sequence alignments do not have equal alphabets."+  | length t /= length b =+    error+      "join: Multi sequence alignments do not have equal lengths."+  | alphabet t /= alphabet b =+    error+      "join: Multi sequence alignments do not have equal alphabets."   | otherwise = Alignment ns ds al (tD === bD)- where-  ns = names t ++ names b-  ds = descriptions t ++ descriptions b-  tD = matrix t-  bD = matrix b-  al = alphabet t+  where+    ns = names t ++ names b+    ds = descriptions t ++ descriptions b+    tD = matrix t+    bD = matrix b+    al = alphabet t  -- | Concatenate two 'Alignment's horizontally. That is, add more -- sites to an alignment. See also 'join'. concat :: Alignment -> Alignment -> Alignment -- left right. concat l r-  | nSequences l /= nSequences r-  = error-    "concat: Multi sequence alignments do not have an equal number of sequences."-  | alphabet l /= alphabet r-  = error "concat: Multi sequence alignments do not have an equal alphabets."-  | names l /= names r-  = error "concat: Multi sequence alignments do not have an equal names."-  | descriptions l /= descriptions r-  = error "concat: Multi sequence alignments do not have an equal descriptions."-  | otherwise-  = Alignment (names l) (descriptions l) (alphabet l) (lD ||| rD)- where-  lD = matrix l-  rD = matrix r+  | nSequences l /= nSequences r =+    error+      "concat: Multi sequence alignments do not have an equal number of sequences."+  | alphabet l /= alphabet r =+    error "concat: Multi sequence alignments do not have an equal alphabets."+  | names l /= names r =+    error "concat: Multi sequence alignments do not have an equal names."+  | descriptions l /= descriptions r =+    error "concat: Multi sequence alignments do not have an equal descriptions."+  | otherwise =+    Alignment (names l) (descriptions l) (alphabet l) (lD ||| rD)+  where+    lD = matrix l+    rD = matrix r  -- | Concatenate a list of 'Alignment's horizontally. See -- 'concat'. concatAlignments :: [Alignment] -> Alignment-concatAlignments []  = error "concatAlignments: Nothing to concatenate."+concatAlignments [] = error "concatAlignments: Nothing to concatenate." concatAlignments [a] = a-concatAlignments as  = foldl' concat (head as) (tail as)+concatAlignments as = foldl' concat (head as) (tail as)  -- Only keep columns from alignment that satisfy given predicate. filterColsWith :: (V.Vector Character -> Bool) -> Alignment -> Alignment-filterColsWith p a = a { matrix = m' }-  where m' = M.fromColumns . filter p . M.toColumns $ matrix a+filterColsWith p a = a {matrix = m'}+  where+    m' = M.fromColumns . filter p . M.toColumns $ matrix a  -- | Only keep columns with standard characters. Alignment columns with IUPAC -- characters are removed.@@ -199,12 +202,13 @@  -- | Filter columns with proportion of standard character larger than given number. filterColsStd :: Double -> Alignment -> Alignment-filterColsStd prop a = filterColsWith-  (\col -> prop * n <= fromIntegral (V.length (V.filter (A.isStd al) col)))-  a- where-  al = alphabet a-  n  = fromIntegral $ nSequences a+filterColsStd prop a =+  filterColsWith+    (\col -> prop * n <= fromIntegral (V.length (V.filter (A.isStd al) col)))+    a+  where+    al = alphabet a+    n = fromIntegral $ nSequences a  -- | Only keep columns without gaps or unknown characters. filterColsNoGaps :: Alignment -> Alignment@@ -218,14 +222,19 @@ -- | Calculcate frequency of characters at each site of a multi sequence alignment. toFrequencyData :: Alignment -> FrequencyData toFrequencyData a = fMapColParChunk 100 (D.frequencyCharacters spec) (matrix a)-  where spec = A.alphabetSpec (alphabet a)+  where+    spec = A.alphabetSpec (alphabet a)  -- | Calculate the distribution of characters. distribution :: FrequencyData -> [Double]-distribution fd = map (/ fromIntegral nSites) $ V.toList $ foldl1-  (V.zipWith (+))-  (M.toColumns fd)-  where nSites = M.cols fd+distribution fd =+  map (/ fromIntegral nSites) $+    V.toList $+      foldl1+        (V.zipWith (+))+        (M.toColumns fd)+  where+    nSites = M.cols fd  -- | Diversity analysis. See 'kEffEntropy'. kEffEntropy :: FrequencyData -> [Double]@@ -239,25 +248,28 @@ -- alignment. countIUPACChars :: Alignment -> Int countIUPACChars a = V.length . V.filter (A.isIUPAC (alphabet a)) $ allChars-  where allChars = M.flatten $ matrix a+  where+    allChars = M.flatten $ matrix a  -- | Count the number of gaps in the alignment. countGaps :: Alignment -> Int countGaps a = V.length . V.filter (A.isGap (alphabet a)) $ allChars-  where allChars = M.flatten $ matrix a+  where+    allChars = M.flatten $ matrix a  -- | Count the number of unknown characters in the alignment. countUnknowns :: Alignment -> Int countUnknowns a = V.length . V.filter (A.isUnknown (alphabet a)) $ allChars-  where allChars = M.flatten $ matrix a+  where+    allChars = M.flatten $ matrix a  -- | Sample the given sites from a multi sequence alignment. subSample :: [Int] -> Alignment -> Alignment-subSample is a = a { matrix = m' } where m' = subSampleMatrix is $ matrix a+subSample is a = a {matrix = m'} where m' = subSampleMatrix is $ matrix a  -- | Randomly sample a given number of sites of the multi sequence alignment.-randomSubSample-  :: PrimMonad m => Int -> Alignment -> Gen (PrimState m) -> m Alignment+randomSubSample ::+  PrimMonad m => Int -> Alignment -> Gen (PrimState m) -> m Alignment randomSubSample n a g = do   let l = length a   is <- replicateM n $ uniformR (0, l - 1) g
src/ELynx/Data/Sequence/Defaults.hs view
@@ -1,23 +1,19 @@-{- |-Module      :  ELynx.Defaults-Description :  Various default values-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Fri Oct  5 23:00:17 2018.---}--+-- |+-- Module      :  ELynx.Defaults+-- Description :  Various default values+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Fri Oct  5 23:00:17 2018. module ELynx.Data.Sequence.Defaults-  ( nameWidth-  , summaryLength-  , summaryNSequences-  , fieldWidth+  ( nameWidth,+    summaryLength,+    summaryNSequences,+    fieldWidth,   ) where 
src/ELynx/Data/Sequence/Sequence.hs view
@@ -1,66 +1,69 @@ {-# LANGUAGE OverloadedStrings #-} -{- |-Module      :  ELynx.Data.Sequence-Description :  Hereditary sequences-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later+-- |+-- Module      :  ELynx.Data.Sequence+-- Description :  Hereditary sequences+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Thu Oct  4 18:54:51 2018.+--+-- This module is to be imported qualified.+module ELynx.Data.Sequence.Sequence+  ( -- * Types+    Name,+    Description,+    Characters,+    Sequence (..), -Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable+    -- * Input+    fromByteString, -Creation date: Thu Oct  4 18:54:51 2018.+    -- * Output+    toByteString,+    header,+    summarize,+    summarizeSequences,+    body, -This module is to be imported qualified.+    -- * Analysis+    length,+    equalLength,+    longest, --}+    -- * Manipulation+    trim,+    concat,+    concatSequences, -module ELynx.Data.Sequence.Sequence-  ( -- * Types-    Name-  , Description-  , Characters-  , Sequence(..)-  -- * Input-  , fromByteString-  -- * Output-  , toByteString-  , header-  , summarize-  , summarizeSequences-  , body-  -- * Analysis-  , length-  , equalLength-  , longest-  -- * Manipulation-  , trim-  , concat-  , concatSequences-  -- * Filtering-  , filterShorterThan-  , filterLongerThan-  , filterStandard+    -- * Filtering+    filterShorterThan,+    filterLongerThan,+    filterStandard,   ) where -import           Control.Parallel.Strategies-import qualified Data.ByteString.Lazy.Char8    as L-import           Data.List                      ( maximumBy )-import           Data.Ord                       ( comparing )-import qualified Data.Vector.Unboxed           as V-import           Prelude                 hiding ( concat-                                                , length-                                                )-import qualified Prelude                       as Pr-                                                ( length )-import qualified Text.Printf                   as P--import qualified ELynx.Data.Alphabet.Alphabet  as A-import           ELynx.Data.Alphabet.Character-import           ELynx.Data.Sequence.Defaults-import           ELynx.Tools+import Control.Parallel.Strategies+import qualified Data.ByteString.Lazy.Char8 as L+import Data.List (maximumBy)+import Data.Ord (comparing)+import qualified Data.Vector.Unboxed as V+import qualified ELynx.Data.Alphabet.Alphabet as A+import ELynx.Data.Alphabet.Character+import ELynx.Data.Sequence.Defaults+import ELynx.Tools+import qualified Text.Printf as P+import Prelude hiding+  ( concat,+    length,+  )+import qualified Prelude as Pr+  ( length,+  )  -- | For now, 'Name's are just 'L.ByteString's. type Name = L.ByteString@@ -81,28 +84,32 @@  -- | Sequences have a name, a possibly empty description, a code and hopefully a -- lot of data.-data Sequence = Sequence { name        :: Name-                         , description :: Description-                         , alphabet    :: A.Alphabet-                         , characters  :: Characters }+data Sequence = Sequence+  { name :: Name,+    description :: Description,+    alphabet :: A.Alphabet,+    characters :: Characters+  }   deriving (Show, Eq)  getInfo :: Sequence -> L.ByteString-getInfo s = L.unwords-  [ alignLeft nameWidth (name s)-  , alignRight fieldWidth (L.pack $ show $ alphabet s)-  , alignRight fieldWidth (L.pack . show $ len)-  , alignRight fieldWidth (L.pack $ P.printf "%2.2f" pGaps)-  ]- where-  len   = length s-  nGaps = countGaps s-  pGaps = 100 * fromIntegral nGaps / fromIntegral len :: Double+getInfo s =+  L.unwords+    [ alignLeft nameWidth (name s),+      alignRight fieldWidth (L.pack $ show $ alphabet s),+      alignRight fieldWidth (L.pack . show $ len),+      alignRight fieldWidth (L.pack $ P.printf "%2.2f" pGaps)+    ]+  where+    len = length s+    nGaps = countGaps s+    pGaps = 100 * fromIntegral nGaps / fromIntegral len :: Double  -- | Trim and show a 'Sequence'. summarize :: Sequence -> L.ByteString-summarize s = L.unwords-  [getInfo s, summarizeByteString summaryLength $ toByteString (characters s)]+summarize s =+  L.unwords+    [getInfo s, summarizeByteString summaryLength $ toByteString (characters s)]  -- | Trim and show a list of 'Sequence's. summarizeSequences :: [Sequence] -> L.ByteString@@ -110,36 +117,38 @@  -- | Header printed before 'Sequence' list. tableHeader :: L.ByteString-tableHeader = L.unwords-  [ alignLeft nameWidth "Name"-  , alignRight fieldWidth "Code"-  , alignRight fieldWidth "Length"-  , alignRight fieldWidth "Gaps [%]"-  , "Sequence"-  ]+tableHeader =+  L.unwords+    [ alignLeft nameWidth "Name",+      alignRight fieldWidth "Code",+      alignRight fieldWidth "Length",+      alignRight fieldWidth "Gaps [%]",+      "Sequence"+    ]  -- | A short description of the sequence. header :: [Sequence] -> L.ByteString header ss =-  L.unlines-    $  reportIfSubsetIsShown-    ++ [ L.pack-       $  "For each sequence, the "-       ++ show summaryLength-       ++ " first bases are shown."-       , L.pack $ "List contains " ++ show (Pr.length ss) ++ " sequences."-       , ""-       , tableHeader-       ]- where-  l = Pr.length ss-  s =-    show summaryNSequences-      ++ " out of "-      ++ show (Pr.length ss)-      ++ " sequences are shown."-  reportIfSubsetIsShown | l > summaryNSequences = [L.pack s]-                        | otherwise             = []+  L.unlines $+    reportIfSubsetIsShown+      ++ [ L.pack $+             "For each sequence, the "+               ++ show summaryLength+               ++ " first bases are shown.",+           L.pack $ "List contains " ++ show (Pr.length ss) ++ " sequences.",+           "",+           tableHeader+         ]+  where+    l = Pr.length ss+    s =+      show summaryNSequences+        ++ " out of "+        ++ show (Pr.length ss)+        ++ " sequences are shown."+    reportIfSubsetIsShown+      | l > summaryNSequences = [L.pack s]+      | otherwise = []  -- | Trim and show a list of 'Sequence's. body :: [Sequence] -> L.ByteString@@ -168,35 +177,35 @@ -- | Concatenate two sequences. 'Name's have to match. concat :: Sequence -> Sequence -> Sequence concat (Sequence i d c cs) (Sequence j f k ks)-  | i /= j-  = error-    $  "concatenate: Sequences do not have equal names: "-    ++ L.unpack i-    ++ ", "-    ++ L.unpack j-    ++ "."-  | d /= f-  = error-    $  "concatenate: Sequences do not have equal descriptions: "-    ++ L.unpack d-    ++ ", "-    ++ L.unpack f-    ++ "."-  | c /= k-  = error-    $  "concatenate: Sequences do not have equal alphabets: "-    ++ show c-    ++ ", "-    ++ show k-    ++ "."-  | otherwise-  = Sequence i d c (cs <> ks)+  | i /= j =+    error $+      "concatenate: Sequences do not have equal names: "+        ++ L.unpack i+        ++ ", "+        ++ L.unpack j+        ++ "."+  | d /= f =+    error $+      "concatenate: Sequences do not have equal descriptions: "+        ++ L.unpack d+        ++ ", "+        ++ L.unpack f+        ++ "."+  | c /= k =+    error $+      "concatenate: Sequences do not have equal alphabets: "+        ++ show c+        ++ ", "+        ++ show k+        ++ "."+  | otherwise =+    Sequence i d c (cs <> ks)  -- | Concatenate a list of sequences, see 'concat'. concatSequences :: [[Sequence]] -> [Sequence]-concatSequences []   = error "concatenateSequences: Nothing to concatenate."+concatSequences [] = error "concatenateSequences: Nothing to concatenate." concatSequences [ss] = ss-concatSequences sss  = foldl1 (zipWith concat) sss+concatSequences sss = foldl1 (zipWith concat) sss  -- | Only take 'Sequence's that are shorter than a given number. filterShorterThan :: Int -> [Sequence] -> [Sequence]
src/ELynx/Data/Sequence/Translate.hs view
@@ -1,50 +1,47 @@-{- |-Module      :  ELynx.Data.Sequence.Translate-Description :  Translate sequences-Copyright   :  (c) Dominik Schrempf 2020-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Fri May 17 13:49:18 2019.---}-+-- |+-- Module      :  ELynx.Data.Sequence.Translate+-- Description :  Translate sequences+-- Copyright   :  (c) Dominik Schrempf 2020+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Fri May 17 13:49:18 2019. module ELynx.Data.Sequence.Translate-  ( translateSeq+  ( translateSeq,   ) where -import qualified Data.Vector.Unboxed           as V--import           ELynx.Data.Alphabet.Alphabet+import qualified Data.Vector.Unboxed as V+import ELynx.Data.Alphabet.Alphabet import qualified ELynx.Data.Alphabet.Character as C-import           ELynx.Data.Character.Codon-import           ELynx.Data.Sequence.Sequence-import           ELynx.Tools+import ELynx.Data.Character.Codon+import ELynx.Data.Sequence.Sequence+import ELynx.Tools  -- | Translate a sequence from 'DNA' or 'DNAX' to 'ProteinS'. translateSeq :: UniversalCode -> Int -> Sequence -> Sequence translateSeq uc rf (Sequence n d a cs) = case a of-  DNA  -> Sequence n d ProteinS (cs' $ translate uc)+  DNA -> Sequence n d ProteinS (cs' $ translate uc)   DNAX -> Sequence n d ProteinS (cs' $ translateX uc)   DNAI -> Sequence n d ProteinI (cs' $ translateI uc)-  _    -> error "translate: can only translate DNA, DNAX, and DNAI."-  where cs' f = C.fromCVec $ translateVecWith f rf (C.toCVec cs)+  _ -> error "translate: can only translate DNA, DNAX, and DNAI."+  where+    cs' f = C.fromCVec $ translateVecWith f rf (C.toCVec cs)  -- Translate from DNA to Protein with given reading frame (0, 1, 2).-translateVecWith-  :: (V.Unbox a, Ord a, V.Unbox b)-  => (Codon a -> b)-  -> Int-  -> V.Vector a-  -> V.Vector b+translateVecWith ::+  (V.Unbox a, Ord a, V.Unbox b) =>+  (Codon a -> b) ->+  Int ->+  V.Vector a ->+  V.Vector b translateVecWith f rf cs-  | rf > 2    = error "translateVecWith: reading frame is larger than 2."-  | rf < 0    = error "translateVecWith: reading frame is negative."+  | rf > 2 = error "translateVecWith: reading frame is larger than 2."+  | rf < 0 = error "translateVecWith: reading frame is negative."   | otherwise = aas- where-  codons = map unsafeFromVec $ chopVec 3 $ V.drop rf cs-  aas    = V.fromList $ map f codons+  where+    codons = map unsafeFromVec $ chopVec 3 $ V.drop rf cs+    aas = V.fromList $ map f codons
src/ELynx/Export/Sequence/Fasta.hs view
@@ -1,30 +1,25 @@-{- |-Module      :  ELynx.Export.Sequence.Fasta-Description :  Export Fasta sequences-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later---Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Write FASTA files.--[NCBI file specifications](https://blast.ncbi.nlm.nih.gov/Blast.cgi?CMD=Web&PAGE_TYPE=BlastDocs&DOC_TYPE=BlastHelp).---}--+-- |+-- Module      :  ELynx.Export.Sequence.Fasta+-- Description :  Export Fasta sequences+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Write FASTA files.+--+-- [NCBI file specifications](https://blast.ncbi.nlm.nih.gov/Blast.cgi?CMD=Web&PAGE_TYPE=BlastDocs&DOC_TYPE=BlastHelp). module ELynx.Export.Sequence.Fasta-  ( sequenceToFasta-  , sequencesToFasta+  ( sequenceToFasta,+    sequencesToFasta,   ) where -import qualified Data.ByteString.Lazy.Char8    as L--import           ELynx.Data.Sequence.Sequence+import qualified Data.ByteString.Lazy.Char8 as L+import ELynx.Data.Sequence.Sequence  fastaHeader :: L.ByteString -> L.ByteString -> L.ByteString fastaHeader n d =
src/ELynx/Import/Sequence/Fasta.hs view
@@ -1,45 +1,42 @@ {-# LANGUAGE BangPatterns #-} -{- |-Module      :  ELynx.Import.Sequence.Fasta-Description :  Import Fasta sequences-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later---Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Parse FASTA files.--[NCBI file specifications](https://blast.ncbi.nlm.nih.gov/Blast.cgi?CMD=Web&PAGE_TYPE=BlastDocs&DOC_TYPE=BlastHelp).--For more complicated parsers, try to use a [lexer](https://hackage.haskell.org/package/megaparsec-7.0.1/docs/Text-Megaparsec-Byte-Lexer.html).--}--+-- |+-- Module      :  ELynx.Import.Sequence.Fasta+-- Description :  Import Fasta sequences+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Parse FASTA files.+--+-- [NCBI file specifications](https://blast.ncbi.nlm.nih.gov/Blast.cgi?CMD=Web&PAGE_TYPE=BlastDocs&DOC_TYPE=BlastHelp).+--+-- For more complicated parsers, try to use a [lexer](https://hackage.haskell.org/package/megaparsec-7.0.1/docs/Text-Megaparsec-Byte-Lexer.html). module ELynx.Import.Sequence.Fasta-  ( Parser-  , fastaSequence-  , fasta+  ( Parser,+    fastaSequence,+    fasta,   ) where -import           Control.Monad-import qualified Data.ByteString.Lazy.Char8    as L-import qualified Data.Set                      as S-import           Data.Void-import           Data.Word8                     ( Word8-                                                , isAlphaNum-                                                )-import           Text.Megaparsec-import           Text.Megaparsec.Byte--import           ELynx.Data.Alphabet.Alphabet  as A-import           ELynx.Data.Alphabet.Character-import           ELynx.Data.Sequence.Sequence-import           ELynx.Tools+import Control.Monad+import qualified Data.ByteString.Lazy.Char8 as L+import qualified Data.Set as S+import Data.Void+import Data.Word8+  ( Word8,+    isAlphaNum,+  )+import ELynx.Data.Alphabet.Alphabet as A+import ELynx.Data.Alphabet.Character+import ELynx.Data.Sequence.Sequence+import ELynx.Tools+import Text.Megaparsec+import Text.Megaparsec.Byte  -- | Shortcut. type Parser = Parsec Void L.ByteString@@ -66,9 +63,9 @@ -- this set only has to be calculcated once per sequence in 'fastaSequence'. sequenceLine :: S.Set Word8 -> Parser L.ByteString sequenceLine s = do-  -- FIXME: Will fail for non-capital letters.+  -- XXX: Will fail for non-capital letters.   !xs <- takeWhile1P (Just "Alphabet character") (`S.member` s)-  _   <- void eol <|> eof+  _ <- void eol <|> eof   return xs  -- XXX: If sequences are parsed line by line, the lines have to be copied when@@ -80,7 +77,7 @@   (n, d) <- sequenceHeader   let !alph = S.map toWord (A.all . alphabetSpec $ a)   lns <- some (sequenceLine alph)-  _   <- many eol+  _ <- many eol   return $ Sequence n d a (fromByteString $ L.concat lns)  -- | Parse a Fasta file with given 'Alphabet'.
test/ELynx/Data/Alphabet/DistributionDiversitySpec.hs view
@@ -1,26 +1,22 @@-{- |-Module      :  ELynx.Data.Alphabet.DistributionDiversitySpec-Copyright   :  (c) Dominik Schrempf 2020-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Mon Feb 25 13:41:12 2019.---}-+-- |+-- Module      :  ELynx.Data.Alphabet.DistributionDiversitySpec+-- Copyright   :  (c) Dominik Schrempf 2020+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Mon Feb 25 13:41:12 2019. module ELynx.Data.Alphabet.DistributionDiversitySpec-  ( spec+  ( spec,   ) where -import qualified Data.Vector.Unboxed           as V-import           Test.Hspec--import           ELynx.Data.Alphabet.DistributionDiversity-import           ELynx.Tools+import qualified Data.Vector.Unboxed as V+import ELynx.Data.Alphabet.DistributionDiversity+import ELynx.Tools+import Test.Hspec  testArr1 :: V.Vector Double testArr1 = V.replicate 20 0.0@@ -34,28 +30,25 @@  spec :: Spec spec = do-  describe "entropy" $ it "calculates entropy of vectors" $ do-    entropy testArr1 `shouldBe` 0.0-    entropy testArr2 `shouldBe` 0.0-    entropy testArr3 `shouldSatisfy` nearlyEq 0.9773805948045555--  describe "kEffEntropy"-    $ it "calculates the effective number of used states using entropy"-    $ do+  describe "entropy" $+    it "calculates entropy of vectors" $ do+      entropy testArr1 `shouldBe` 0.0+      entropy testArr2 `shouldBe` 0.0+      entropy testArr3 `shouldSatisfy` nearlyEq 0.9773805948045555+  describe "kEffEntropy" $+    it "calculates the effective number of used states using entropy" $+      do         kEffEntropy testArr1 `shouldBe` 1.0         kEffEntropy testArr2 `shouldBe` 1.0         kEffEntropy testArr3 `shouldSatisfy` nearlyEq 2.6574860842252765--  describe "homoplasy" $ it "calculates homoplasy of vectors" $ do-    homoplasy testArr1 `shouldBe` 0.0-    homoplasy testArr2 `shouldBe` 1.0-    homoplasy testArr3 `shouldSatisfy` nearlyEq 0.74--  describe "kEffHomoplasy"-    $ it "calculates the effective number of used states using homoplasy"-    $ do+  describe "homoplasy" $+    it "calculates homoplasy of vectors" $ do+      homoplasy testArr1 `shouldBe` 0.0+      homoplasy testArr2 `shouldBe` 1.0+      homoplasy testArr3 `shouldSatisfy` nearlyEq 0.74+  describe "kEffHomoplasy" $+    it "calculates the effective number of used states using homoplasy" $+      do         kEffHomoplasy testArr1 `shouldSatisfy` isInfinite         kEffHomoplasy testArr2 `shouldBe` 1.0         kEffHomoplasy testArr3 `shouldSatisfy` nearlyEq 1.3513513513513513--
test/ELynx/Data/Sequence/AlignmentSpec.hs view
@@ -1,30 +1,26 @@-{- |-Module      :  ELynx.Data.Sequence.AlignmentSpec-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Fri Oct  5 14:25:42 2018.---}-+-- |+-- Module      :  ELynx.Data.Sequence.AlignmentSpec+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Fri Oct  5 14:25:42 2018. module ELynx.Data.Sequence.AlignmentSpec-  ( spec+  ( spec,   ) where -import qualified Data.ByteString.Lazy.Char8    as L-import qualified Data.Matrix.Unboxed           as M-import           Test.Hspec--import           ELynx.Data.Alphabet.Alphabet-import           ELynx.Data.Alphabet.Character-import           ELynx.Data.Sequence.Alignment-import           ELynx.Import.Sequence.Fasta-import           ELynx.Tools+import qualified Data.ByteString.Lazy.Char8 as L+import qualified Data.Matrix.Unboxed as M+import ELynx.Data.Alphabet.Alphabet+import ELynx.Data.Alphabet.Character+import ELynx.Data.Sequence.Alignment+import ELynx.Import.Sequence.Fasta+import ELynx.Tools+import Test.Hspec  fastaNucleotideIUPACFN :: FilePath fastaNucleotideIUPACFN = "data/NucleotideIUPAC.fasta"@@ -33,16 +29,19 @@ ssData = M.fromLists $ map (reverse . map fromChar) ["AAA", "GAA", "TAA"]  ssA :: Alignment-ssA = Alignment (map L.pack ["SEQUENCE_1", "SEQUENCE_2", "SEQUENCE_3"])-                (replicate 3 L.empty)-                DNAI-                ssData+ssA =+  Alignment+    (map L.pack ["SEQUENCE_1", "SEQUENCE_2", "SEQUENCE_3"])+    (replicate 3 L.empty)+    DNAI+    ssData  spec :: Spec-spec = describe "subSample" $ it "correctly sub sample an Alignment" $ do-  a <--    either error id-    .   fromSequences-    <$> parseFileWith (fasta DNAI) fastaNucleotideIUPACFN-  let ss = subSample [0, 3, 5] a-  ss `shouldBe` ssA+spec = describe "subSample" $+  it "correctly sub sample an Alignment" $ do+    a <-+      either error id+        . fromSequences+        <$> parseFileWith (fasta DNAI) fastaNucleotideIUPACFN+    let ss = subSample [0, 3, 5] a+    ss `shouldBe` ssA
test/ELynx/Data/Sequence/SequenceSpec.hs view
@@ -1,28 +1,24 @@-{- |-Module      :  ELynx.Data.Sequence.SequenceSpec-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Fri Oct  5 14:25:42 2018.---}-+-- |+-- Module      :  ELynx.Data.Sequence.SequenceSpec+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Fri Oct  5 14:25:42 2018. module ELynx.Data.Sequence.SequenceSpec-  ( spec+  ( spec,   ) where -import qualified Data.ByteString.Lazy.Char8    as L-import           Test.Hspec--import           ELynx.Data.Alphabet.Alphabet-import           ELynx.Data.Sequence.Sequence-import           ELynx.Import.Sequence.Fasta-import           ELynx.Tools+import qualified Data.ByteString.Lazy.Char8 as L+import ELynx.Data.Alphabet.Alphabet+import ELynx.Data.Sequence.Sequence+import ELynx.Import.Sequence.Fasta+import ELynx.Tools+import Test.Hspec  fastaDifferentLengthFN :: FilePath fastaDifferentLengthFN = "data/NucleotideDifferentLength.fasta"@@ -31,23 +27,26 @@ fastaDifferentLengthTrimmedFN = "data/NucleotideDifferentLengthTrimmed.fasta"  longestSequenceInFileBS :: L.ByteString-longestSequenceInFileBS = L.unlines-  $ map L.pack [">SEQUENCE_3", "ATTTAAAAAAACCCAAAACCCGGGCCCCGGGTTTTTTTA"]+longestSequenceInFileBS =+  L.unlines $+    map L.pack [">SEQUENCE_3", "ATTTAAAAAAACCCAAAACCCGGGCCCCGGGTTTTTTTA"]  longestSequenceInFile :: Sequence-longestSequenceInFile = parseByteStringWith "Fasta byte string"-                                            (fastaSequence DNA)-                                            longestSequenceInFileBS+longestSequenceInFile =+  parseByteStringWith+    "Fasta byte string"+    (fastaSequence DNA)+    longestSequenceInFileBS  spec :: Spec spec = do-  describe "longest" $ it "finds the longest sequence" $ do-    ss <- parseFileWith (fasta DNA) fastaDifferentLengthFN-    longest ss `shouldBe` longestSequenceInFile--  describe "filterLongerThan"-    $ it "filters sequences that are longer than a specified length"-    $ do-        ss  <- parseFileWith (fasta DNA) fastaDifferentLengthFN+  describe "longest" $+    it "finds the longest sequence" $ do+      ss <- parseFileWith (fasta DNA) fastaDifferentLengthFN+      longest ss `shouldBe` longestSequenceInFile+  describe "filterLongerThan" $+    it "filters sequences that are longer than a specified length" $+      do+        ss <- parseFileWith (fasta DNA) fastaDifferentLengthFN         ss' <- parseFileWith (fasta DNA) fastaDifferentLengthTrimmedFN         filterLongerThan 10 ss `shouldBe` ss'
test/ELynx/Data/Sequence/TranslateSpec.hs view
@@ -1,28 +1,24 @@-{- |-Module      :  ELynx.Data.Sequence.TranslateSpec-Copyright   :  (c) Dominik Schrempf 2018-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Fri Oct  5 14:25:42 2018.---}-+-- |+-- Module      :  ELynx.Data.Sequence.TranslateSpec+-- Copyright   :  (c) Dominik Schrempf 2018+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Fri Oct  5 14:25:42 2018. module ELynx.Data.Sequence.TranslateSpec-  ( spec+  ( spec,   ) where -import           Test.Hspec--import           ELynx.Data.Alphabet.Alphabet-import           ELynx.Data.Character.Codon-import           ELynx.Data.Sequence.Translate-import           ELynx.Import.Sequence.Fasta-import           ELynx.Tools+import ELynx.Data.Alphabet.Alphabet+import ELynx.Data.Character.Codon+import ELynx.Data.Sequence.Translate+import ELynx.Import.Sequence.Fasta+import ELynx.Tools+import Test.Hspec  fastaTranslateDNAFN :: FilePath fastaTranslateDNAFN = "data/TranslateMitochondrialVertebrateDNA.fasta"@@ -32,7 +28,8 @@  spec :: Spec spec =-  describe "translateDNAX" $ it "correctly translates a test sequence" $ do-    ss  <- parseFileWith (fasta DNAX) fastaTranslateDNAFN-    ss' <- parseFileWith (fasta ProteinS) fastaTranslateProteinFN-    map (translateSeq VertebrateMitochondrial 0) ss `shouldBe` ss'+  describe "translateDNAX" $+    it "correctly translates a test sequence" $ do+      ss <- parseFileWith (fasta DNAX) fastaTranslateDNAFN+      ss' <- parseFileWith (fasta ProteinS) fastaTranslateProteinFN+      map (translateSeq VertebrateMitochondrial 0) ss `shouldBe` ss'
test/ELynx/Export/Sequence/FastaSpec.hs view
@@ -1,41 +1,38 @@-{- |-Module      :  ELynx.Export.Sequence.FastaSpec-Copyright   :  (c) Dominik Schrempf 2020-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Fri Jan 18 09:59:57 2019.---}-+-- |+-- Module      :  ELynx.Export.Sequence.FastaSpec+-- Copyright   :  (c) Dominik Schrempf 2020+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Fri Jan 18 09:59:57 2019. module ELynx.Export.Sequence.FastaSpec-  ( spec+  ( spec,   ) where -import           Test.Hspec--import           ELynx.Data.Alphabet.Alphabet-import           ELynx.Export.Sequence.Fasta-import           ELynx.Import.Sequence.Fasta-import           ELynx.Tools+import ELynx.Data.Alphabet.Alphabet+import ELynx.Export.Sequence.Fasta+import ELynx.Import.Sequence.Fasta+import ELynx.Tools+import Test.Hspec  fastaNucleotideIUPACFN :: FilePath fastaNucleotideIUPACFN = "data/NucleotideIUPAC.fasta"  spec :: Spec spec =-  describe "sequencesToFasta"-    $ it-        "should create a fasta bytestring that, when parsed again, is the original sequence"-    $ do+  describe "sequencesToFasta" $+    it+      "should create a fasta bytestring that, when parsed again, is the original sequence"+      $ do         ss <- parseFileWith (fasta DNAI) fastaNucleotideIUPACFN-        let f   = sequencesToFasta ss-            ss' = parseByteStringWith-              "Fasta byte string created from sequence object"-              (fasta DNAI)-              f+        let f = sequencesToFasta ss+            ss' =+              parseByteStringWith+                "Fasta byte string created from sequence object"+                (fasta DNAI)+                f         ss `shouldBe` ss'
test/ELynx/Import/Sequence/FastaSpec.hs view
@@ -1,28 +1,24 @@-{- |-Module      :  ELynx.Import.Sequence.FastaSpec-Copyright   :  (c) Dominik Schrempf 2020-License     :  GPL-3.0-or-later--Maintainer  :  dominik.schrempf@gmail.com-Stability   :  unstable-Portability :  portable--Creation date: Fri Jan 18 09:54:38 2019.---}-+-- |+-- Module      :  ELynx.Import.Sequence.FastaSpec+-- Copyright   :  (c) Dominik Schrempf 2020+-- License     :  GPL-3.0-or-later+--+-- Maintainer  :  dominik.schrempf@gmail.com+-- Stability   :  unstable+-- Portability :  portable+--+-- Creation date: Fri Jan 18 09:54:38 2019. module ELynx.Import.Sequence.FastaSpec-  ( spec+  ( spec,   ) where -import           Data.Either-import           Test.Hspec--import           ELynx.Data.Alphabet.Alphabet+import Data.Either+import ELynx.Data.Alphabet.Alphabet import qualified ELynx.Data.Sequence.Alignment as M-import           ELynx.Import.Sequence.Fasta-import           ELynx.Tools+import ELynx.Import.Sequence.Fasta+import ELynx.Tools+import Test.Hspec  fastaNucleotideFN :: FilePath fastaNucleotideFN = "data/Nucleotide.fasta"@@ -41,33 +37,28 @@   it "parses a fasta file with nucleotide sequences with equal length" $ do     a <-       either error id-      .   M.fromSequences-      <$> parseFileWith (fasta DNA) fastaNucleotideFN+        . M.fromSequences+        <$> parseFileWith (fasta DNA) fastaNucleotideFN     M.nSequences a `shouldBe` 3     M.length a `shouldBe` 40--  it "parses a fasta file with nucleotide IUPAC sequences with equal length"-    $ do-        a <--          either error id-          .   M.fromSequences+  it "parses a fasta file with nucleotide IUPAC sequences with equal length" $+    do+      a <-+        either error id+          . M.fromSequences           <$> parseFileWith (fasta DNAI) fastaNucleotideIUPACFN-        M.nSequences a `shouldBe` 3-        M.length a `shouldBe` 40-+      M.nSequences a `shouldBe` 3+      M.length a `shouldBe` 40   it "should not parse erroneous files" $ do     ea <- runParserOnFile (fasta DNAI) fastaErroneousFN     ea `shouldSatisfy` isLeft-   it "parses a fasta file with amino acid sequences with equal length" $ do     a <-       either error id-      .   M.fromSequences-      <$> parseFileWith (fasta Protein) fastaAminoAcidFN+        . M.fromSequences+        <$> parseFileWith (fasta Protein) fastaAminoAcidFN     M.nSequences a `shouldBe` 2     M.length a `shouldBe` 237-   it "should not parse erroneous files" $ do     a <- runParserOnFile (fasta ProteinI) fastaErroneousFN     a `shouldSatisfy` isLeft-