From e880f5848a26305581b7b1ee199ee28ae77acc47 Mon Sep 17 00:00:00 2001 From: Mark Henderson Date: Tue, 5 Oct 2021 10:12:56 -0500 Subject: [PATCH] Update docs (#1) * Convert docs to Codon --- CONTRIBUTING.md | 16 +- README.md | 82 +-- docs/doxygen/Doxyfile | 2 +- docs/sphinx/Makefile | 2 +- docs/sphinx/_ext/codon.py | 157 ++++++ docs/sphinx/build.rst | 10 +- docs/sphinx/conf.py | 30 +- docs/sphinx/cookbook.rst | 273 ---------- docs/sphinx/docgen.py | 38 +- docs/sphinx/embed.rst | 23 +- docs/sphinx/index.rst | 73 ++- docs/sphinx/intro.rst | 37 +- docs/sphinx/logo.png | Bin 212915 -> 22923 bytes docs/sphinx/make.bat | 2 +- docs/sphinx/parallel.rst | 28 +- docs/sphinx/python.rst | 30 +- docs/sphinx/seqlex.py | 245 --------- docs/sphinx/tutorial/index.rst | 3 +- docs/sphinx/tutorial/pipelines.rst | 52 ++ docs/sphinx/tutorial/primer.rst | 258 ++++------ docs/sphinx/tutorial/setup.rst | 18 +- docs/sphinx/tutorial/tutorial.rst | 411 --------------- docs/sphinx/tutorial/workshop.rst | 770 ----------------------------- docs/workshop/section1.codon | 8 - docs/workshop/section2.codon | 18 - docs/workshop/section3.codon | 29 -- docs/workshop/section4.codon | 36 -- docs/workshop/section5.codon | 42 -- docs/workshop/section6.codon | 43 -- stdlib/time.codon | 2 +- 30 files changed, 479 insertions(+), 2259 deletions(-) create mode 100644 docs/sphinx/_ext/codon.py delete mode 100644 docs/sphinx/cookbook.rst delete mode 100644 docs/sphinx/seqlex.py create mode 100644 docs/sphinx/tutorial/pipelines.rst delete mode 100644 docs/sphinx/tutorial/tutorial.rst delete mode 100644 docs/sphinx/tutorial/workshop.rst delete mode 100644 docs/workshop/section1.codon delete mode 100644 docs/workshop/section2.codon delete mode 100644 docs/workshop/section3.codon delete mode 100644 docs/workshop/section4.codon delete mode 100644 docs/workshop/section5.codon delete mode 100644 docs/workshop/section6.codon diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 9611492f..6469ac92 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -1,10 +1,10 @@ -# Contributing to Seq +# Contributing to Codon -Thank you for considering contributing to Seq! This document contains some helpful information for getting started. The best place to ask questions or get feedback is [our Gitter chatroom](https://gitter.im/seq-lang/Seq). For a high-level outline of the features we aim to add in the future, check the [roadmap](https://github.com/seq-lang/seq/wiki/Roadmap). +Thank you for considering contributing to Codon! This document contains some helpful information for getting started. The best place to ask questions or get feedback is [our Gitter chatroom](https://gitter.im/seq-lang/Seq). For a high-level outline of the features we aim to add in the future, check the [roadmap](https://github.com/seq-lang/seq/wiki/Roadmap). ## Development workflow -All development is done on the [`develop`](https://github.com/seq-lang/seq/tree/develop) branch. Just before release, we bump the version number, merge into [`master`](https://github.com/seq-lang/seq/tree/master) and tag the build with a tag of the form `vX.Y.Z` where `X`, `Y` and `Z` are the [SemVer](https://semver.org) major, minor and patch numbers, respectively. Our Travis CI build script automatically builds and deploys tagged commits as a new GitHub release via our trusty [@SeqBot](https://github.com/seqbot). It also builds and deploys the documentation to our website. +All development is done on the [`develop`](https://github.com/exaloop/codon/tree/develop) branch. Just before release, we bump the version number, merge into [`master`](https://github.com/exaloop/codon/tree/master) and tag the build with a tag of the form `vX.Y.Z` where `X`, `Y` and `Z` are the [SemVer](https://semver.org) major, minor and patch numbers, respectively. Our Travis CI build script automatically builds and deploys tagged commits as a new GitHub release via our trusty [@SeqBot](https://github.com/seqbot). It also builds and deploys the documentation to our website. ## Coding standards @@ -12,7 +12,7 @@ All C++ code should be formatted with [ClangFormat](https://clang.llvm.org/docs/ ## Writing tests -Tests are written as Seq programs. The [`test/core/`](https://github.com/seq-lang/seq/tree/master/test/core) directory contains some examples. If you add a new test file, be sure to add it to [`test/main.cpp`](https://github.com/seq-lang/seq/blob/master/test/main.cpp) so that it will be executed as part of the test suite. There are two ways to write tests for Seq: +Tests are written as Codon programs. The [`test/core/`](https://github.com/exaloop/codon/tree/master/test/core) directory contains some examples. If you add a new test file, be sure to add it to [`test/main.cpp`](https://github.com/exaloop/codon/blob/master/test/main.cpp) so that it will be executed as part of the test suite. There are two ways to write tests for Codon: #### New style @@ -39,7 +39,7 @@ print(2 + 2) # EXPECT: 4 ## Pull requests -Pull requests should generally be based on the `develop` branch. Before submitting a pull request, pleace make sure... +Pull requests should generally be based on the `develop` branch. Before submitting a pull request, please make sure... - ... to provide a clear description of the purpose of the pull request. - ... to include tests for any new or changed code. @@ -49,12 +49,12 @@ Please be patient with pull request reviews, as our throughput is limited! ## Issues -We use [GitHub's issue tracker](https://github.com/seq-lang/seq/issues), so that's where you'll find the most recent list of open bugs, feature requests and general issues. If applicable, we try to tag each issue with at least one of the following tags: +We use [GitHub's issue tracker](https://github.com/exaloop/codon/issues), so that's where you'll find the most recent list of open bugs, feature requests, and general issues. If applicable, we try to tag each issue with at least one of the following tags: -- `Build`: Issues related to building Seq +- `Build`: Issues related to building Codon - `Codegen`: Issues related to code generation (i.e. after parsing and type checking) - `Parser`: Issues related to lexing/parsing -- `Library`: Issues related to the Seq standard library +- `Library`: Issues related to the Codon standard library - `Interop`: Issues related to interoperability with other languages or systems - `Docs`: Issues related to documentation - `Feature`: New language feature proposals diff --git a/README.md b/README.md index 2668153b..00fe0730 100644 --- a/README.md +++ b/README.md @@ -1,24 +1,24 @@

- Seq + Codon

-

Seq — a language for bioinformatics

+

Codon

- - + Build Status Gitter - - + Version - - + License

@@ -27,17 +27,17 @@ > **A strongly-typed and statically-compiled high-performance Pythonic language!** -Seq is a programming language for computational genomics and bioinformatics. With a Python-compatible syntax and a host of domain-specific features and optimizations, Seq makes writing high-performance genomics software as easy as writing Python code, and achieves performance comparable to (and in many cases better than) C/C++. +Codon is a programming language for computationally intensive workloads. With a Python-compatible syntax and a host of domain-specific features and optimizations, Codon makes writing high-performance software as easy as writing Python code, and achieves performance comparable to (and in many cases better than) C/C++. -**Think of Seq as a strongly-typed and statically-compiled Python: all the bells and whistles of Python, boosted with a strong type system, without any performance overhead.** +**Think of Codon as a strongly-typed and statically-compiled Python: all the bells and whistles of Python, boosted with a strong type system, without any performance overhead.** -Seq is able to outperform Python code by up to 160x. Seq can further beat equivalent C/C++ code by up to 2x without any manual interventions, and also natively supports parallelism out of the box. Implementation details and benchmarks are discussed [in our paper](https://dl.acm.org/citation.cfm?id=3360551). +Codon is able to outperform Python code by up to 160x. Codon can further beat equivalent C/C++ code by up to 2x without any manual interventions, and also natively supports parallelism out of the box. Implementation details and benchmarks are discussed [in our paper](https://dl.acm.org/citation.cfm?id=3360551). -Learn more by following the [tutorial](https://docs.seq-lang.org/tutorial) or from the [cookbook](https://docs.seq-lang.org/cookbook). +Learn more by following the [tutorial](https://docs.exaloop.io/tutorial). ## Examples -Seq is a Python-compatible language, and many Python programs should work with few if any modifications: +Codon is a Python-compatible language, and many Python programs should work with few if any modifications: ```python def fib(n): @@ -49,7 +49,7 @@ def fib(n): fib(1000) ``` -This prime counting example showcases Seq's [OpenMP](https://www.openmp.org/) support, enabled with the addition of one line. The `@par` annotation tells the compiler to parallelize the following for-loop, in this case using a dynamic schedule, chunk size of 100, and 16 threads. +This prime counting example showcases Codon's [OpenMP](https://www.openmp.org/) support, enabled with the addition of one line. The `@par` annotation tells the compiler to parallelize the following for-loop, in this case using a dynamic schedule, chunk size of 100, and 16 threads. ```python from sys import argv @@ -72,30 +72,11 @@ for i in range(2, limit): print(total) ``` -Here is an example showcasing some of Seq's bioinformatics features, which include native sequence and k-mer types. - -```python -from bio import * -s = s'ACGTACGT' # sequence literal -print(s[2:5]) # subsequence -print(~s) # reverse complement -kmer = Kmer[8](s) # convert to k-mer - -# iterate over length-3 subsequences -# with step 2 -for sub in s.split(3, step=2): - print(sub[-1]) # last base - - # iterate over 2-mers with step 1 - for kmer in sub.kmers(step=1, k=2): - print(~kmer) # '~' also works on k-mers -``` - ## Install ### Pre-built binaries -Pre-built binaries for Linux and macOS on x86_64 are available alongside [each release](https://github.com/seq-lang/seq/releases). We also have a script for downloading and installing pre-built versions: +Pre-built binaries for Linux and macOS on x86_64 are available alongside [each release](https://github.com/exaloop/codon/releases). We also have a script for downloading and installing pre-built versions: ```bash /bin/bash -c "$(curl -fsSL https://seq-lang.org/install.sh)" @@ -107,35 +88,4 @@ See [Building from Source](docs/sphinx/build.rst). ## Documentation -Please check [docs.seq-lang.org](https://docs.seq-lang.org) for in-depth documentation. - -## Citing Seq - -If you use Seq in your research, please cite: - -> Ariya Shajii, Ibrahim Numanagić, Riyadh Baghdadi, Bonnie Berger, and Saman Amarasinghe. 2019. Seq: a high-performance language for bioinformatics. *Proc. ACM Program. Lang.* 3, OOPSLA, Article 125 (October 2019), 29 pages. DOI: https://doi.org/10.1145/3360551 - -BibTeX: - -``` -@article{Shajii:2019:SHL:3366395.3360551, - author = {Shajii, Ariya and Numanagi\'{c}, Ibrahim and Baghdadi, Riyadh and Berger, Bonnie and Amarasinghe, Saman}, - title = {Seq: A High-performance Language for Bioinformatics}, - journal = {Proc. ACM Program. Lang.}, - issue_date = {October 2019}, - volume = {3}, - number = {OOPSLA}, - month = oct, - year = {2019}, - issn = {2475-1421}, - pages = {125:1--125:29}, - articleno = {125}, - numpages = {29}, - url = {http://doi.acm.org/10.1145/3360551}, - doi = {10.1145/3360551}, - acmid = {3360551}, - publisher = {ACM}, - address = {New York, NY, USA}, - keywords = {Python, bioinformatics, computational biology, domain-specific language, optimization, programming language}, -} -``` +Please check [docs.exaloop.io](https://docs.exaloop.io) for in-depth documentation. diff --git a/docs/doxygen/Doxyfile b/docs/doxygen/Doxyfile index c15e2c5c..32cc2df9 100644 --- a/docs/doxygen/Doxyfile +++ b/docs/doxygen/Doxyfile @@ -1,4 +1,4 @@ -PROJECT_NAME = "seq" +PROJECT_NAME = "codon" XML_OUTPUT = xml INPUT = ../../compiler/include ../../compiler/lang ../../compiler/types ../../compiler/util STRIP_FROM_PATH = ../.. diff --git a/docs/sphinx/Makefile b/docs/sphinx/Makefile index bb23c9e8..63966934 100644 --- a/docs/sphinx/Makefile +++ b/docs/sphinx/Makefile @@ -4,7 +4,7 @@ # You can set these variables from the command line. SPHINXOPTS = SPHINXBUILD = sphinx-build -SPHINXPROJ = seq +SPHINXPROJ = codon SOURCEDIR = . BUILDDIR = _build diff --git a/docs/sphinx/_ext/codon.py b/docs/sphinx/_ext/codon.py new file mode 100644 index 00000000..58bcd1dc --- /dev/null +++ b/docs/sphinx/_ext/codon.py @@ -0,0 +1,157 @@ +from collections import defaultdict + +import re + +from typing import Any,Dict,Iterable,Iterator,List,NamedTuple,Tuple +from typing import cast + +from docutils.parsers.rst import directives +from sphinx import addnodes +from sphinx.directives import ObjectDescription +from sphinx.domains import Domain +from sphinx.domains import Index +from sphinx.roles import XRefRole +from sphinx.util.nodes import make_refnode +from sphinx.locale import _,__ +from docutils import nodes +from docutils.nodes import Element,Node +from docutils.parsers.rst import directives + +from sphinx import addnodes +from sphinx.addnodes import pending_xref,desc_signature +from sphinx.application import Sphinx +from sphinx.builders import Builder +from sphinx.directives import ObjectDescription +from sphinx.domains import Domain,ObjType,Index,IndexEntry +from sphinx.environment import BuildEnvironment +from sphinx.locale import _,__ +from sphinx.pycode.ast import ast,parse as ast_parse +from sphinx.roles import XRefRole +from sphinx.util import logging +from sphinx.util.docfields import Field,GroupedField,TypedField +from sphinx.util.docutils import SphinxDirective +from sphinx.util.inspect import signature_from_str +from sphinx.util.nodes import make_id,make_refnode +from sphinx.util.typing import TextlikeNode + +import sphinx.domains.python + +codon_sig_re=re.compile(r'''^([\w.]*\.)?(\w+)\s*(?:\[\s*(.*)\s*\])?\s*(?:\(\s*(.*)\s*\)(?:\s*->\s*(.*))?)?$''',re.VERBOSE) + + +def handle_signature(self,sig: str,signode: desc_signature) -> Tuple[str,str]: + m=codon_sig_re.match(sig) + if m is None: + raise ValueError + prefix,name,generics,arglist,retann=m.groups() + + # determine module and class name (if applicable), as well as full name + modname=self.options.get('module',self.env.ref_context.get('py:module')) + classname=self.env.ref_context.get('py:class') + isextension=self.objtype=='extension' + if classname: + add_module=False + if prefix and (prefix==classname or prefix.startswith(classname+".")): + fullname=prefix+name + # class name is given again in the signature + prefix=prefix[len(classname):].lstrip('.') + elif prefix: + # class name is given in the signature, but different + # (shouldn't happen) + fullname=classname+'.'+prefix+name + else: + # class name is not given in the signature + fullname=classname+'.'+name + else: + add_module=True + if prefix: + classname=prefix.rstrip('.') + fullname=prefix+name + else: + classname='' + fullname=name + + signode['module']=modname + if modname.startswith('..'): # HACK: no idea why this happens + modname=modname[2:] + signode['class']=classname + signode['fullname']=fullname + + sig_prefix=self.get_signature_prefix(sig) + if sig_prefix: + signode+=addnodes.desc_annotation(sig_prefix,sig_prefix) + + if not isextension: + if prefix: + signode+=addnodes.desc_addname(prefix,prefix) + elif add_module and self.env.config.add_module_names: + if modname and modname!='exceptions': + # exceptions are a special case, since they are documented in the + # 'exceptions' module. + nodetext=modname+'.' + signode+=addnodes.desc_addname(nodetext,nodetext) + signode+=addnodes.desc_name(name,name) + else: + ref=type_to_xref(str(name),self.env) + signode+=addnodes.desc_name(name,name) + + if generics: + signode+=addnodes.desc_name("generics","["+generics+"]") + if arglist: + try: + signode+=sphinx.domains.python._parse_arglist(arglist,self.env) + except SyntaxError: + # fallback to parse arglist original parser. + # it supports to represent optional arguments (ex. "func(foo [, bar])") + sphinx.domains.python._pseudo_parse_arglist(signode,arglist) + except NotImplementedError as exc: + logger.warning("could not parse arglist (%r): %s",arglist,exc,location=signode) + sphinx.domains.python._pseudo_parse_arglist(signode,arglist) + else: + if self.needs_arglist(): + # for callables, add an empty parameter list + signode+=addnodes.desc_parameterlist() + + if retann: + children=sphinx.domains.python._parse_annotation(retann,self.env) + signode+=addnodes.desc_returns(retann,'',*children) + + anno=self.options.get('annotation') + if anno: + signode+=addnodes.desc_annotation(' '+anno,' '+anno) + + return fullname,prefix + + +sphinx.domains.python.PyObject.handle_signature=handle_signature + +from sphinx.domains.python import * + +logger=logging.getLogger(__name__) + + +class CodonDomain(PythonDomain): + name='codon' + label='Codon' + object_types={'function':ObjType(_('function'),'func','obj'),# 'data': ObjType(_('data'), 'data', 'obj'), + 'class':ObjType(_('class'),'class','exc','obj'),'type':ObjType(_('class'),'exc','class','obj'),'extension':ObjType(_('class'),'exc','class','obj'), + 'exception':ObjType(_('exception'),'exc','class','obj'),'method':ObjType(_('method'),'meth','obj'),# 'classmethod': ObjType(_('class method'), 'meth', 'obj'), + # 'staticmethod': ObjType(_('static method'), 'meth', 'obj'), + # 'attribute': ObjType(_('attribute'), 'attr', 'obj'), + 'module':ObjType(_('module'),'mod','obj'),} # type: Dict[str, ObjType] + + directives={'function':PyFunction,'data':PyVariable,'class':PyClasslike,'exception':PyClasslike,'type':PyClasslike,'extension':PyClasslike,'method':PyMethod,'classmethod':PyClassMethod, + 'staticmethod':PyStaticMethod,'attribute':PyAttribute,'module':PyModule,'currentmodule':PyCurrentModule,'decorator':PyDecoratorFunction,'decoratormethod':PyDecoratorMethod,} + roles={'data':PyXRefRole(),'exc':PyXRefRole(),'func':PyXRefRole(fix_parens=True),'class':PyXRefRole(),# 'const': PyXRefRole(), + 'attr':PyXRefRole(),'meth':PyXRefRole(fix_parens=True),'mod':PyXRefRole(),'obj':PyXRefRole(),} + initial_data={'objects':{}, # fullname -> docname, objtype + 'modules':{}, # modname -> docname, synopsis, platform, deprecated + } # type: Dict[str, Dict[str, Tuple[Any]]] + indices=[PythonModuleIndex,] + + +def setup(app): + app.add_domain(CodonDomain) + # app.connect('object-description-simplify', filter_meta_fields) + + return {'version':'0.1','parallel_read_safe':True,'parallel_write_safe':True,} diff --git a/docs/sphinx/build.rst b/docs/sphinx/build.rst index 6eb99105..00e2c062 100644 --- a/docs/sphinx/build.rst +++ b/docs/sphinx/build.rst @@ -1,13 +1,13 @@ Building from Source ==================== -Unless you really need to build Seq for whatever reason, we strongly +Unless you really need to build Codon for whatever reason, we strongly recommend using pre-built binaries if possible. Dependencies ------------ -Seq depends on LLVM 12, which can be installed via most package managers. To +Codon depends on LLVM 12, which can be installed via most package managers. To build LLVM 12 yourself, you can do the following: .. code-block:: bash @@ -28,7 +28,7 @@ build LLVM 12 yourself, you can do the following: Build ----- -The following can generally be used to build Seq. The build process will automatically +The following can generally be used to build Codon. The build process will automatically download and build several smaller dependencies. .. code-block:: bash @@ -40,5 +40,5 @@ download and build several smaller dependencies. -DCMAKE_CXX_COMPILER=clang++) cmake --build build --config Release -This should produce the ``seqc`` executable in the ``build`` directory, as well as -``seqtest`` which runs the test suite. +This should produce the ``codon`` executable in the ``build`` directory, as well as +``codon_test`` which runs the test suite. diff --git a/docs/sphinx/conf.py b/docs/sphinx/conf.py index bdc1e28c..a8cea4ed 100644 --- a/docs/sphinx/conf.py +++ b/docs/sphinx/conf.py @@ -16,17 +16,13 @@ import os import sys sys.path.insert(0, os.path.abspath("./_ext")) -def setup(sphinx): - sys.path.insert(0, os.path.abspath('.')) - from seqlex import SeqLexer - sphinx.add_lexer("seq", SeqLexer) # -- Project information ----------------------------------------------------- -project = u'Seq' -copyright = u'2019-2021, seq-lang' -author = u'seq-lang' +project = u'Codon' +copyright = u'2019-2021, codon' +author = u'codon' # The short X.Y version version = u'0.11' @@ -50,9 +46,9 @@ extensions = [ 'sphinx.ext.mathjax', 'sphinx.ext.githubpages', 'sphinx.ext.intersphinx', - 'seq' # 'breathe', - # 'exhale' + # 'exhale', + 'codon', ] # Add any paths that contain templates here, relative to this directory. @@ -95,7 +91,7 @@ html_theme = 'sphinx_book_theme' # documentation. # html_theme_options = { - "repository_url": "https://github.com/seq-lang/seq", + "repository_url": "https://github.com/exaloop/codon", "repository_branch": "develop", "path_to_docs": "docs/sphinx/", "use_repository_button": True, @@ -120,7 +116,7 @@ html_sidebars = { '**': ['globaltoc.html', 'relations.html', 'searchbox.html'], # -- Options for HTMLHelp output --------------------------------------------- # Output file base name for HTML help builder. -htmlhelp_basename = 'seqdoc' +htmlhelp_basename = 'codondoc' # -- Options for LaTeX output ------------------------------------------------ @@ -147,7 +143,7 @@ latex_elements = { # (source start file, target name, title, # author, documentclass [howto, manual, or own class]). latex_documents = [ - (master_doc, 'seq.tex', u'seq Documentation', + (master_doc, 'codon.tex', u'Codon Documentation', u'arshajii', 'manual'), ] @@ -157,7 +153,7 @@ latex_documents = [ # One entry per manual page. List of tuples # (source start file, name, description, authors, manual section). man_pages = [ - (master_doc, 'seq', u'Seq Documentation', + (master_doc, 'codon', u'Codon Documentation', [author], 1) ] @@ -168,18 +164,18 @@ man_pages = [ # (source start file, target name, title, author, # dir menu entry, description, category) texinfo_documents = [ - (master_doc, 'seq', u'Seq Documentation', - author, 'seq', 'a language for bioinformatics', + (master_doc, 'codon', u'Codon Documentation', + author, 'codon', 'a high-performance language', 'Miscellaneous'), ] # -- Extension configuration ------------------------------------------------- breathe_projects = { - 'Seq': '../doxygen/xml' + 'Codon': '../doxygen/xml' } -breathe_default_project = 'Seq' +breathe_default_project = 'Codon' exhale_args = { # These arguments are required diff --git a/docs/sphinx/cookbook.rst b/docs/sphinx/cookbook.rst deleted file mode 100644 index 9107aa8b..00000000 --- a/docs/sphinx/cookbook.rst +++ /dev/null @@ -1,273 +0,0 @@ -Cookbook -======== - -.. contents:: - -Subsequence extraction ----------------------- - -.. code-block:: seq - - myseq = s'CAATAGAGACTAAGCATTAT' - sublen = 5 - stride = 2 - - # explicit for-loop - for subseq in myseq.split(sublen, stride): - print(subseq) - - # pipelined - myseq |> split(sublen, stride) |> print - -k-mer extraction ----------------- - -.. code-block:: seq - - myseq = s'CAATAGAGACTAAGCATTAT' - stride = 2 - - # explicit for-loop - for subseq in myseq.kmers(stride, k=5): - print(subseq) - - # pipelined - myseq |> kmers(stride, k=5) |> print - -Reverse complementation ------------------------ - -.. code-block:: seq - - # sequences - s = s'GGATC' - print(~s) # GATCC - - # k-mers - k = k'GGATC' - print(~k) # GATCC - -k-mer Hamming distance ----------------------- - -.. code-block:: seq - - k1 = k'ACGTC' - k2 = k'ACTTA' - # ^ ^ - print(abs(k1 - k2)) # Hamming distance = 2 - -k-mer Hamming neighbors ------------------------ - -.. code-block:: seq - - def neighbors(kmer): - for i in range(len(kmer)): - for b in (k'A', k'C', k'G', k'T'): - if kmer[i] != b: - yield kmer |> base(i, b) - - print(list(neighbors(k'AGC'))) # CGC, GGC, etc. - -k-mer minimizer ---------------- - -.. code-block:: seq - - def minimizer(s, k: Static[int]): - assert len(s) >= k - kmer_min = Kmer[k](s[:k]) - for kmer in s[1:].kmers(k=k, step=1): - kmer = min(kmer, ~kmer) - if kmer < kmer_min: kmer_min = kmer - return kmer_min - - print(minimizer(s'ACGTACGTACGT', 10)) - -de Bruijn edge --------------- - -.. code-block:: seq - - def de_bruijn_edge(a, b): - a = a |> base(0, k'A') # reset first base: [T]GAG -> [A]GAG - b = b >> s'A' # shift right to A: [GAG]C -> A[GAG] - return a == b # suffix of a == prefix of b - - print(de_bruijn_edge(k'TGAG', k'GAGC')) # True - print(de_bruijn_edge(k'TCAG', k'GAGC')) # False - -Count bases ------------ - -.. code-block:: seq - - @tuple - class BaseCount: - A: int - C: int - G: int - T: int - - def __add__(self, other: BaseCount): - a1, c1, g1, t1 = self - a2, c2, g2, t2 = other - return (a1 + a2, c1 + c2, g1 + g2, t1 + t2) - - def count_bases(s): - match s: - case 'A*': return count_bases(s[1:]) + (1,0,0,0) - case 'C*': return count_bases(s[1:]) + (0,1,0,0) - case 'G*': return count_bases(s[1:]) + (0,0,1,0) - case 'T*': return count_bases(s[1:]) + (0,0,0,1) - case _: return BaseCount(0,0,0,0) - - print(count_bases(s'ACCGGGTTTT')) # (A: 1, C: 2, G: 3, T: 4) - -Spaced seed search ------------------- - -.. code-block:: seq - - def has_spaced_acgt(s): - match s: - case 'A_C_G_T*': - return True - case t if len(t) >= 8: - return has_spaced_acgt(s[1:]) - case _: - return False - - print(has_spaced_acgt(s'AAATCTGTTAAA')) # True - print(has_spaced_acgt(s'ACGTACGTACGT')) # False - -Reverse-complement palindrome ------------------------------ - -.. code-block:: seq - - def is_own_revcomp(s): - match s: - case 'A*T' | 'T*A' | 'C*G' | 'G*C': - return is_own_revcomp(s[1:-1]) - case '': - return True - case _: - return False - - print(is_own_revcomp(s'ACGT')) # True - print(is_own_revcomp(s'ATTA')) # False - -Sequence alignment ------------------- - -.. code-block:: seq - - # default parameters - s1 = s'CGCGAGTCTT' - s2 = s'CGCAGAGTT' - aln = s1 @ s2 - print(aln.cigar, aln.score) # 3M1I6M -3 - - # custom parameters - # match = 2; mismatch = 4; gap1(k) = 2k + 4; gap2(k) = k + 13 - aln = s1.align(s2, a=2, b=4, gapo=4, gape=2, gapo2=13, gape2=1) - print(aln.cigar, aln.score) # 3M1D3M2I2M 2 - -Reading FASTA/FASTQ -------------------- - -.. code-block:: seq - - # iterate over everything - for r in FASTA('genome.fa'): - print(r.name) - print(r.seq) - - # iterate over sequences - for s in FASTA('genome.fa') |> seqs: - print(s) - - # iterate over everything - for r in FASTQ('reads.fq'): - print(r.name) - print(r.read) - print(r.qual) - - # iterate over sequences - for s in FASTQ('reads.fq') |> seqs: - print(s) - -Reading paired-end FASTQ ------------------------- - -.. code-block:: seq - - for r1, r2 in zip(FASTQ('reads_1.fq'), FASTQ('reads_2.fq')): - print(r1.name, r2.name) - print(r1.read, r2.read) - print(r1.qual, r2.qual) - -Parallel FASTQ processing -------------------------- - -.. code-block:: seq - - def process(s: seq): - ... - - # OMP_NUM_THREADS environment variable controls threads - FASTQ('reads.fq') |> iter ||> process - - # Sometimes batching reads into blocks can improve performance, - # especially if each is quick to process. - FASTQ('reads.fq') |> blocks(size=1000) ||> iter |> process - -Reading SAM/BAM/CRAM --------------------- - -.. code-block:: seq - - # iterate over everything - for r in SAM('alignments.sam'): - print(r.name) - print(r.read) - print(r.pos) - print(r.mapq) - print(r.cigar) - print(r.reversed) - # etc. - - for r in BAM('alignments.bam'): - # ... - - for r in CRAM('alignments.cram'): - # ... - - # iterate over sequences - for s in SAM('alignments.sam') |> seqs: - print(s) - - for s in BAM('alignments.bam') |> seqs: - print(s) - - for s in CRAM('alignments.cram') |> seqs: - print(s) - -DNA to protein translation --------------------------- - -.. code-block:: seq - - dna = s'AGGTCTAACGGC' - protein = dna |> translate - print(protein) # RSNG - -Reading protein sequences from FASTA ------------------------------------- - -.. code-block:: seq - - for s in pFASTA('seqs.fasta') |> seqs: - print(s) diff --git a/docs/sphinx/docgen.py b/docs/sphinx/docgen.py index 582d8b2d..9d45e187 100755 --- a/docs/sphinx/docgen.py +++ b/docs/sphinx/docgen.py @@ -17,23 +17,23 @@ root=os.path.abspath(sys.argv[1]) print(f"Generating documentation for {root}...") -# 1. Call seqc -docstr and get a documentation in JSON format +# 1. Call codon -docstr and get a documentation in JSON format def load_json(directory): - # Get all seq files in the directory + # Get all codon files in the directory files=[] for root,_,items in os.walk(directory): for f in items: - if f.endswith('.seq'): + if f.endswith('.codon'): files.append(os.path.abspath(os.path.join(root,f))) files='\n'.join(files) - s=sp.run(['../../build/seqc','doc'],stdout=sp.PIPE,input=files.encode('utf-8')) + s=sp.run(['../../build/codon','doc'],stdout=sp.PIPE,input=files.encode('utf-8')) if s.returncode!=0: - raise ValueError('seqc failed') + raise ValueError('codon failed') return json.loads(s.stdout.decode('utf-8')) j=load_json(root) -print(f" - Done with seqc") +print(f" - Done with codon") # with open('x.json','w') as f: # json.dump(j,f,indent=2) @@ -48,8 +48,8 @@ for mid,module in modules.items(): print(root,mid,module) directory=os.path.relpath(directory,root) # remove the prefix os.makedirs(f"stdlib/{directory}",exist_ok=True) - if name.endswith('.seq'): - name=name[:-4] + if name.endswith('.codon'): + name=name[:-6] # drop suffix if name!='__init__': parsed_modules[directory].add((name,mid)) module=os.path.split(module)[0] @@ -57,7 +57,7 @@ for directory,modules in parsed_modules.items(): module=directory.replace('/','.') with open(f'stdlib/{directory}/index.rst','w') as f: if module!='.': - print(f".. seq:module:: {module}\n",file=f) + print(f".. codon:module:: {module}\n",file=f) print(f"{module}",file=f) else: print("Standard Library Reference",file=f) @@ -143,11 +143,11 @@ for directory,(name,mid) in {(d,m) for d,mm in parsed_modules.items() for m in m if name=='__init__': file,mode=f'stdlib/{directory}/index.rst','a' with open(file,mode) as f: - print(f".. seq:module:: {module}\n",file=f) - print(f":seq:mod:`{module}`",file=f) - print("-"*(len(module)+11)+"\n",file=f) + print(f".. codon:module:: {module}\n",file=f) + print(f":codon:mod:`{module}`",file=f) + print("-"*(len(module)+13)+"\n",file=f) directory_prefix=directory+'/' if directory!='.' else '' - print(f"Source code: `{directory_prefix}{name}.seq `_\n",file=f) + print(f"Source code: `{directory_prefix}{name}.codon `_\n",file=f) if 'doc' in j[mid]: print(parse_docstr(j[mid]['doc']),file=f) @@ -162,13 +162,13 @@ for directory,(name,mid) in {(d,m) for d,mm in parsed_modules.items() for m in m if v['kind']=='class': if v['name'].endswith('Error'): v["type"]="exception" - f.write(f'.. seq:{v["type"]}:: {v["name"]}') + f.write(f'.. codon:{v["type"]}:: {v["name"]}') if 'generics' in v and v['generics']: f.write(f'[{",".join(v["generics"])}]') elif v['kind']=='function': - f.write(f'.. seq:function:: {v["name"]}{parse_fn(v)}') + f.write(f'.. codon:function:: {v["name"]}{parse_fn(v)}') elif v['kind']=='variable': - f.write(f'.. seq:data:: {v["name"]}') + f.write(f'.. codon:data:: {v["name"]}') # if v['kind'] == 'class' and v['type'] == 'extension': # f.write(f'**`{getLink(v["parent"])}`**') # else: @@ -202,7 +202,7 @@ for directory,(name,mid) in {(d,m) for d,mm in parsed_modules.items() for m in m print(' **Properties:**\n',file=f) for c in props: v=j[c] - f.write(f' .. seq:attribute:: {v["name"]}\n') + f.write(f' .. codon:attribute:: {v["name"]}\n') if 'doc' in v: f.write("\n"+parse_docstr(v['doc'],4)+"\n\n") f.write("\n") @@ -212,7 +212,7 @@ for directory,(name,mid) in {(d,m) for d,mm in parsed_modules.items() for m in m print(' **Magic methods:**\n',file=f) for c in magics: v=j[c] - f.write(f' .. seq:method:: {v["name"]}{parse_fn(v,True)}\n') + f.write(f' .. codon:method:: {v["name"]}{parse_fn(v,True)}\n') f.write(' :noindex:\n') if 'doc' in v: f.write("\n"+parse_docstr(v['doc'],4)+"\n\n") @@ -222,7 +222,7 @@ for directory,(name,mid) in {(d,m) for d,mm in parsed_modules.items() for m in m print(' **Methods:**\n',file=f) for c in methods: v=j[c] - f.write(f' .. seq:method:: {v["name"]}{parse_fn(v,True)}\n') + f.write(f' .. codon:method:: {v["name"]}{parse_fn(v,True)}\n') if 'doc' in v: f.write("\n"+parse_docstr(v['doc'],4)+"\n\n") f.write("\n") diff --git a/docs/sphinx/embed.rst b/docs/sphinx/embed.rst index db33b818..a643ac1d 100644 --- a/docs/sphinx/embed.rst +++ b/docs/sphinx/embed.rst @@ -1,9 +1,9 @@ -Calling Seq from C/C++ -====================== +Calling Codon from C/C++ +======================== -Calling C/C++ from Seq is quite easy with ``from C import``, but Seq can also be called from C/C++ code. To make a Seq function externally visible, simply annotate it with ``@export``: +Calling C/C++ from Codon is quite easy with ``from C import``, but Codon can also be called from C/C++ code. To make a Codon function externally visible, simply annotate it with ``@export``: -.. code-block:: seq +.. code-block:: python @export def foo(n: int): @@ -11,14 +11,14 @@ Calling C/C++ from Seq is quite easy with ``from C import``, but Seq can also be print(i * i) return n * n -Note that only top-level, non-generic functions can be exported. Now we can create a shared library containing ``foo`` (assuming source file *foo.seq*): +Note that only top-level, non-generic functions can be exported. Now we can create a shared library containing ``foo`` (assuming source file *foo.codon*): .. code-block:: bash - seqc build -o foo.o foo.seq - gcc -shared -lseqrt -lomp foo.o -o libfoo.so + codon build -o foo.o foo.codon + gcc -shared -lcodonrt -lomp foo.o -o libfoo.so -(The last command might require an additional ``-L/path/to/seqrt/lib/`` argument if ``libseqrt`` is not installed on a standard path.) +(The last command might require an additional ``-L/path/to/codonrt/lib/`` argument if ``libcodonrt`` is not installed on a standard path.) Now we can call ``foo`` from a C program: @@ -39,22 +39,21 @@ Compile: gcc -o foo -L. -lfoo foo.c -Now running ``./foo`` should invoke ``foo()`` as defined in Seq, with an argument of ``10``. +Now running ``./foo`` should invoke ``foo()`` as defined in Codon, with an argument of ``10``. Converting types ---------------- -The following table shows the conversions between Seq and C/C++ types: +The following table shows the conversions between Codon and C/C++ types: ============ ============ - Seq C/C++ + Codon C/C++ ------------ ------------ ``int`` ``int64_t`` ``float`` ``double`` ``bool`` ``bool`` ``byte`` ``int8_t`` ``str`` ``{int64_t, char*}`` -``seq`` ``{int64_t, char*}`` ``class`` Pointer to corresponding tuple ``@tuple`` Struct of fields ============ ============ diff --git a/docs/sphinx/index.rst b/docs/sphinx/index.rst index 721c171d..98d875fe 100644 --- a/docs/sphinx/index.rst +++ b/docs/sphinx/index.rst @@ -1,7 +1,22 @@ -**Seq** — a Python implementation for bioinformatics +**Codon** - a high-performance Python implementation ==================================================== -Seq is a Pythonic language for computational genomics and bioinformatics. With a Python-compatible syntax and a host of domain-specific features and optimizations, Seq makes writing high-performance genomics software as easy as writing Python code, and achieves performance comparable to (and in many cases better than) C/C++. +What is Codon? +-------------- + +Codon is a high-performance Python implementation that compiles Python code to native machine code without any runtime overhead. +The Codon framework grew out of the `Seq `_ project; while Seq focuses on genomics and bioinformatics, Codon +can be applied in a number of different areas and is extensible via a plugin system. + +Typical speedups over Python are on the order of 10-100x or more, on a single thread. Codon supports native multithreading which can lead +to speedups many times higher still. + +What isn't Codon? +----------------- + +While Codon supports nearly all of Python's syntax, it is not a drop-in replacement, and large codebases might require modifications +to be run through the Codon compiler. For example, some of Python's modules are not yet implemented within Codon, and a few of Python's +dynamic features are disallowed. The Codon compiler produces detailed error messages to help identify and resolve any incompatibilities. Questions, comments or suggestions? Visit our `Gitter chatroom `_. @@ -13,62 +28,36 @@ Questions, comments or suggestions? Visit our `Gitter chatroom `_ for Python, `SeqAn `_ for C++ and `BioJulia `_ for Julia. In fact, Seq offers a lot of the same functionality found in these libraries. The advantages of having a domain-specific language and compiler, however, are the higher-level constructs and optimizations like :ref:`pipeline`, :ref:`match`, :ref:`interalign` and :ref:`prefetch`, which are difficult to replicate in a library, as they often involve large-scale program transformations/optimizations. A domain-specific language also allows us to explore different backends like GPU, TPU or FPGA in a systematic way, in conjunction with these various constructs/optimizations, which is ongoing work. +Unlike other performance-oriented Python implementations, such as PyPy or Numba, Codon is a standalone system implemented entirely independently +of regular Python. Since it does not need to interoperate with CPython's runtime, Codon has far greater flexibility to generate optimized code. +In fact, Codon will frequently generate the same code as that from an equivalent C or C++ program. This design choice also allows Codon to circumvent +issues like Python's global interpretter lock, and thereby to take full advantage of parallelism and multithreading. *What about interoperability with other languages and frameworks?* -Interoperability is and will continue to be a priority for the Seq project. We don't want using Seq to render you unable to use all the other great frameworks and libraries that exist. Seq already supports interoperability with C/C++ and Python (see :ref:`interop`). +Interoperability is and will continue to be a priority for the Codon project. We don't want using Codon to render you unable to use all the other great +frameworks and libraries that exist. Codon already supports interoperability with C/C++ and Python (see :ref:`interop`). *I want to contribute! How do I get started?* -Great! Check out our `contribution guidelines `_ and `open issues `_ to get started. Also don't hesitate to drop by our `Gitter chatroom `_ if you have any questions. +Great! Check out our `contribution guidelines `_ and `open issues `_ +to get started. Also don't hesitate to drop by our `Gitter chatroom `_ +if you have any questions. *What is planned for the future?* -See the `roadmap `_ for information about this. +See the `roadmap `_ for information about this. diff --git a/docs/sphinx/intro.rst b/docs/sphinx/intro.rst index 6abbc3d6..14df4ec1 100644 --- a/docs/sphinx/intro.rst +++ b/docs/sphinx/intro.rst @@ -7,13 +7,13 @@ Install Pre-built binaries ^^^^^^^^^^^^^^^^^^ -Pre-built binaries for Linux and macOS on x86_64 are available alongside `each release `_. We also have a script for downloading and installing pre-built versions: +Pre-built binaries for Linux and macOS on x86_64 are available alongside `each release `_. We also have a script for downloading and installing pre-built versions: .. code-block:: bash /bin/bash -c "$(curl -fsSL https://seq-lang.org/install.sh)" -This will install Seq in a new ``.seq`` directory within your home directory. +This will install Codon in a new ``.codon`` directory within your home directory. Building from source ^^^^^^^^^^^^^^^^^^^^ @@ -23,56 +23,55 @@ See `Building from Source `_. Usage ----- -The ``seqc`` program can either directly run Seq source in JIT mode: +The ``codon`` program can either directly ``run`` Codon source in JIT mode: .. code-block:: bash - seqc run myprogram.seq + codon run myprogram.codon The default compilation and run mode is *debug* (``-debug``). Compile and run with optimizations with the ``-release`` option: .. code-block:: bash - seqc run -release myprogram.seq + codon run -release myprogram.codon -``seqc`` can also produce executables (ensure you have ``clang`` installed, as it is used for linking): +``codon`` can also ``build`` executables (ensure you have ``clang`` installed, as it is used for linking): .. code-block:: bash # generate 'myprogram' executable - seqc build -exe myprogram.seq + codon build -exe myprogram.codon # generate 'foo' executable - seqc build -o foo myprogram.seq + codon build -o foo myprogram.codon -``seqc`` can produce object files: +``codon`` can produce object files: .. code-block:: bash # generate 'myprogram.o' object file - seqc build -obj myprogram.seq + codon build -obj myprogram.codon # generate 'foo.o' object file - seqc build -o foo.o myprogram.seq + codon build -o foo.o myprogram.codon -``seqc`` can produce LLVM IR: +``codon`` can produce LLVM IR: .. code-block:: bash # generate 'myprogram.ll' object file - seqc build -llvm myprogram.seq + codon build -llvm myprogram.codon # generate 'foo.ll' object file - seqc build -o foo.ll myprogram.seq + codon build -o foo.ll myprogram.codon Compile-time definitions ------------------------ -``seqc`` allows for compile-time definitions via the ``-D`` flag. For example, in the following code: +``codon`` allows for compile-time definitions via the ``-D`` flag. For example, in the following code: -.. code-block:: seq +.. code-block:: python - from bio import * - print(Kmer[SEED_LEN]()) + print(Int[BIT_WIDTH]()) -``SEED_LEN`` can be specified on the command line as such: ``seqc run -DSEED_LEN=10 myprogram.seq``. +``BIT_WIDTH`` can be specified on the command line as such: ``codon run -DBIT_WIDTH=10 myprogram.codon``. diff --git a/docs/sphinx/logo.png b/docs/sphinx/logo.png index 8cc4bc6286cd233a3bbd6869ea1c9532b1529470..ab34227255bf876cf493d75eddbeb2be2ebe4318 100644 GIT binary patch literal 22923 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

e&=Nu}tz*H!6A%T2W?Qc1-r_m3 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

GpV{$ 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

bLfNs+-lsmxUh+m!*iVD>DTY*dmi0 zU-}vGzUmNSE#7^~(gNo}$70Z~J@c8(>s*E4l12u@jI;i8zjAz>b&9C=(Hb}-7&J9* zxWei9S@lr{{BKSL;z+CC*gMTexqnSA1JxBU;0qddOD`$q17!n|w}k#9M}eE{T3&xM zwoXr+SED0CALI_&_J@gUA>GU%q85ByHNCSqeyvP5?=^lQ1Q%T4$lC4^pB6nsGH$a? z9rGB}i|6=|KP>=Qe&^U2PUl@@g{s)t?RXiBd552z#FDR9mqn~RQ-LDB@wq(yf!5xY z!tdEL>z6TJ`w@Ark*M1J)d(w#2JxDpJd)$|_vy%5A4%4M`&dtAFHbm5cCy3{WBPq! z<@q}dS5?fWQpOK^lQNjq;YO|JolYBcx*=NPZAew@@7k4RT^@Z1;B$P|ZQWqdx`%e%oPkKuHzNz&A8q1h z?CRe?9DYL;b!)AQofMiF9!8$d<(d@qr5rztBfrD1+PE*!`IiGMdWG6U5pXZ6S!i7h zqhmW5z`+m2)Z$htoS(!HeP;?AVucqL>m~%P8tlYz7BWk%@na088$K~`?SKhJJBzYwgd3gAsk^^{*AHQX-DfD3PYYvIP zGh;Bz8=G_zPegA;o}p|J7wP3=|6GG^J3*yX4W| zk;b5)*k2z$#!PP|3WTBNkl=-W6@Lhf)(=6_jYz2#tSaTNjy>2>#6@j7mB{4bv51Db zd~ma^xFOvR$Zue;3M&K+kV*g3{8)5T*E=MsH+uP96AWAgk~CP^dq<_YtfOBW{}LlF zW`n@WSlNmTc&pJLt5nSoGax2HuwJSzVWnqg!G&6PV;*)>PbQnvSPO`;n2!~?w6L-` zoMCu)S7lE%zZ|8moi;nYAkU84Q7S_Z_;Q$o7;YpuOmXuxfPxZ>B+wB#6p%OrGE1p;SXFoF@Mh$YgFL2m(chyhXWYnry&+Dxp#iN(H}n<9 zBkE?f9hAiC^G=6f#MgkExWJqVInYP3XLzd9c>~)>W45d=aqn!GYvH0K&@Jju=h zzC069rp1^4%>p3LYyHkT2s4jP$?iB3mPz$8u=0an670rHP885Z?k?SGGz+R@h72sa z($k-=gK^Y^)%F@pxWe14QoYqNv`l$y1FaCg<}YaUn3^a$AoS~h(QXrGVNvuL*eH0_ z+T5$d|GX**Sbz=NLUPM4Rqz)7aE!ujBe(?2(9AbHPjwFuPEsU8kYOy+ZQCQS+A$ch z+}~vwvOPrWC~wQ$AMFY`SRM>UdfLO*$M}-dlvWk;Hu|3`bh)7y2)RFmQ8W-M7+$iYH^W z1s&(|Kc>3bl&?%4h@s?yssw+a>ge|$6U;4 z;k1qleu;w67{=t3RZ_OKRaF@!87!lH2ICj3JlsD zW0G9i0`een)A{7dKbQImD^tq_;Lf&*s9k}{dg`EhyiiwBu6S4L6sg+a7IYXT%yU?mF?+Z+{i$MkK7`lm zvi#TN!iXi|(<~KAtQSDod?x-+ZZuW_Nq|ohqCQ{!C)xaOBkzxIB}2Q*&O4g=x_)e) znLEnITOLZ7#a-XX*Za72UN`4FO}@>?$=;iu3@wsV&_FSB!p#n~v*DhQsYv;Gu+khV z7O;tY^P!13du<=x&8eOX{v+3fUGG0P6?5O#qG~SPw-fakOTQ#w8~>imH?Dt|Z`|%P zr3Z}&MDQqr4R&BFt&$VQ_s$#N$x{+OlZ_J`nUr{)H}jT4dyo>5SbWPNsxJIipCsMg z;iUN{L%BDtK8BTDE9uWCCl*w?MzRNUnYi?HQttwrZvk**P@XY11$8cucWvnZt&1^m zY}qqWF*D1446~SA+H=No?1BXmaWVPjus^87DKR@0Yt7T}IvcCGO?z4$j?E#zwMDU@ zV_Wq|NGul|6S?`#pNA-aU>D?zixPrRp0c`wdO(C21@!=+9wRh>k&@qUmR3pmDmKk+k zH^&cdd+_5rMUBp&!OIpb3>r3Fr;~nvBZ_KWBFP%B9U>oJCY0NX9wtiiCyGFD z0y{-lr!=vtC<0C8y3y4oe!@M}Zy!3rX+Y|gkkP&wEa_?_hH9dby64p5b+uIr-%j=k zFR*CU^9VZvSJ24PZoA*idzgsmU42`WIqc;oUpw{fJX$lOO~mSDu<=vdYe2vR7^h?7 z5sQD0$eP7TA8DR7;aV6)3o&lgW6LDfB8)L@H4A<4&f9RkHc@9VB24|+AxZ&%{?c*2 zyIr55m@#EW2^;#@%V&pbZcG%h5SuH^?8%zwYU4n=B-nUb>rJ0EY}kHXj{9>ExqcyI zmN#zXXR+A$LQq>mgoFL5AqxW00>Q%{H|8`T(;YD3 z^;+X%&BBVbT`4#DHvP&-?#D(dN~gYE@K{rSajv}C0C`F^1q8%{iziN5@ZJ#H zr7G*8RGO5><^o68Oov6f_M5tqkLZF>)&tCfyvYWem9%lK@&;ugD@dHVg?qHAp;E$r z(c)nxdbnO9F>!qcANI?*W4+hJ&A@@Kl|~no0}^&q5NQEECfzO~P?&arn3Wip2~&I$k-T>{m*HYdV#I z6HDm2;tFD+t8v`w%*O@?yFVr#4T@2FHlu~)Nqhxxw+D6^+8#Ngb&ZbFo`BmUS$81; zOml?By`A9HM&*_ioJ-x^SNJo^FDVydC2pJ81kAD&x|&7KZ~B{U?v7c>{6E^CPY;Za zAjqmCX*}B<0jv|Hs;}aFg?+AA@YtGk-HBZpd{(|6UZo)|MN@x@Z~Kcdaztj99`=pq z`Y_!kce(FdAf3g&w7I={1*ca*?arUqQRur?hCZ2tHx9m)D-jS0b?WfJCj})8Oe|oL zUsqgyCp?;N7C+eEwqOhXaAGh_n3o@cOVR_gNl}tU*gIszxuht!wjJ$ zeV;8b#Gv&qu!emx+X*oTqEoXwPjTwVV3S|6~iKQ~GhcJ6Lbl?mV?h2j*{^ z=4;7KRw@ro5x|yJlxMv z$S(DHufgsT5=T+;qwXAGDEYKQAYx)-RQGNVgH+r63uy78=3~_kq=&}pl`lQ+$N+d} zX=c&lP%{>#zfeF}~8 zf4Vn)o4f7kJQ4R;r`*TyTh@|$S?8~IwPWOB!l=Hfvp<-!uPW>xUy3{OtnOW?yT9lv z7yORpa>YdwbH&A4{O(HOxMMi%{%S5X{mU0mb@qp7R~DBrGx3x30ovn?O*DtKr)^*S z$pLQ?L^-8@P{V(GgYp#MGPY;kyGwryQ+(ExzDQ`Pot{|m39Pd+#Q6)c0lC>%HAe_6UcrdJ z?RQl!?^vTcE$)PII?{zbZRmA{D&_8aZCTgTmE{iijNIQ@F*;L>s`vb9dM)tv$)HqH zPZh|lk`P*C80<8^59bLh-(38*^{e2=oPEu)j*f&#e%fvU0oSP0_8Y6V0~Ay(SJ!k? zMy zo9!a8+pR?ax~qvDd$`|I%$wvsYW-Q4L$Rhfz$Czddia#~p!IUo(!8*}F{dx}O)yfb zehv4<}W%&mU&Eg-M=n3dgGdyLk{7w;A(wkPu=N9MX zN6MPl$2ZRGuP$Mdo)8~g$i*m+q845VRk_sNT%3g(`h*4)^^K^oZ0F1G!YaND)thgI z^YTeFu(%jb@x`q8T@uaM7Tlf&1{XTC%K|&pp0#PjM~I(ar#xAFzzf`tZ-T0{AeR21 zM_|CCw=R{3zD@ZDK+jz8?l?5KZI(TN+mQ_eZ4vKV#GjU{_bYabTKQ_x-6V3LLS$sH z*HHSRz%ntrO%rIT?IpM?2ixD=Djr`m+AcQF)y^&|uj2RVR>#9_u}~E=k?Zd?3Mv@0 z11fh3iQ8^v%Yxf0jhphUniJY*e+L61mv)}U9!IB_h!HW1njTK~_8C06QDsOrazo!w!owy>}0H@Xq zA6LU8zcz6&VNABSxR3MDUj9;I)|GKA0iGC zTjBP*5pKlRZQW#q-<6kdmCofjVW&L%&k9|PD^lfRv_@T2-3^pJt6xoB#Eu@r@K&Z z{v{_IUZW=p64lc`BQG@C9m4$#RY8<=AS;%?TX=<*_-Ym|&aAK#bTv^b@7ww3WnOr0 zPk*L=Gv}n2!fNF9?n9E3J#GpUS;)kxU=!jwi$q z2Q5orP(rmvi3{7@ENrFrBK(NJFISJ%Sbx1m*)K5?C(VJd*=Tk5g9T=*GOFRxN zI-S=265BP{(I5MtUEsv)*IOrkzdYIdPzw^ zoclGLDkn^bd|Fx9HrK`fkPFuY;vxx&pJc5DjDmuKlhS+4tBIN)j_g=?FHBEgguuN| zAF$?hZ>xPJ>tBLpVhX3^D2oV6Sg-I<_p8FlrF?b=DG5L*kBlAP`h>-p5A~^iP9cQOmy>M}=5?UzDSN{y#9rdadOULXX{eenX_xwDSvONLJXbIx zA_7tusFELe-J^>+hzGT{$OsYKy0S}p^@CZ>JNgqnJ`(ebQ9fBOd%G_R(m@Is!W zQc0PB^RnE7fH`|A2yNk8y!hxDd|nC{R_$2D7k*B(BO1E{w}qoioU=DYjlX|vgXUWd zgAtyV&SN14-rXe*i>vy*2uE^>NeD2WjG@SC;hWjEx3jpjix?lap1n1CFMe3lLXyNM zn(kX(Iue}3hlc>oSO)YVz1KHVj{1F?gYg0N&#oe5E1E#J&s+-xxHk(ywaH<_wf>IB zbmiANvYPWz?nAuD&b7@gK?nL(V!@vu23Lk+pP2me-U-8SOX%Zzi)Rh2Ki2WrF0C zeyDOPXfA(RSuD&ix4ClFsUW1)BW!h|bIc%-C+vkP`fMkVLwk)-%!jRsLA_k5cCckm z`-W2sdHs-=G~JxF^ZR0#JTQ<1N1!AjFKhM;r<^=4Z$ z&32P1V96$w>%~FoF_G1@sV(UNL%0(ngXS_I{cj{~S%%BKu@ScK>hK!H2VCu=>R_b- zGV#Yl#CqE7z_{-G(|l!rB~it-qKVcYt7Z>tONEihW%xOH#IE==^mRkVrJK;X z_U%vl+xgKXwV*U|L<)RRd*$_p><1U=2F5b`R~X?jedB7B2)+QwU_JWEZsooroMaXq zCyUg(lza4vSYf3yZ#T5vlwN`QE8=~2VbTo&z6ACVsH8#e!3q5#ZF|2+Me{GIXO1JV zRCejd{(i<1igk=0GTL|yk=FwH6}Bx25MfJwm%ALT{;F(Z1y(*292@JT7=*ed)s3vw zN#AW{0Qw>PkQrw1uvIFv=qln2QA^q#*bG(OL0F-#n|?5t{`jcOdR_DJZ)uPGf1ztO zK_C$Nxa4eH@y#v9R7qoDne43l3L3JD*Q=Rr{9%oZp9NT*AvMp66ukTErsvLQxp^=U z%ixJ+RDt40czyQUyus|iE##?$?7~hft*gfN9QG4DkiO|m<#{|@T4pYZ(FMIRzv;vb z0S=ZL5Cv-UF6c#Mz^|Fl9r~a_TwXY&zu!TQRQ7D;~Nfpee^dKGJk0aV*%VSJC zmYRlFGNpm|b5B|=mVW9IO91Iwq<1W-z_z z*<_GO3a^*RI}F;c!FhAjalVsGH?T-{|7;Y9DIwoKw;1oC*LT0f;?D?J`z9-t5gB^@ zo3Y+JJi*qEK0{XqU;Kz9v|OH&zF3wa-2numuhR&odr@1Z z`PWZM!2Gzr$}7PRnsihC`~7vr%9RN&#zt(WaH*Qx%uBpRt?T7Z8KdOtyTG72N0z7B z!CsSBkPWP?OS)mP7UHW{S)Yq%I7$It^J8FiV}5hX?`6+%xhDP>NCeVWnCwR@KeO2- z&IuB{&d}vdPasfwis4V^yX>i1^NSlPcuy8?AX+6;3y;kIJ^$Cr=M?KTHBwqfSwV;N z*W%B>2rBw+jZ2mICh1WRq&GPIT&6?je`00A^lphgme%$2Wv+Zrsc<)5?RZ(foaDDj z>Q(c1cp3Ga@&L*W$JDd9k%YfEN`i23$M zB`rPE;bAO-GUU;Dkq0y$2KV1@(jGUVDJQ{elG zOK?VCV;Lr@n%=S1Tu5c@B0Gkz>Q}o+UGIA5K5b_YfOLTI09VK?7!Doh1pK*;cL4^G zMFN8DTzQ`5!pr{2iYRrCGry>33>W8X!VAo~TofB9uRzEH0mw)y(zj2p%;+s1zIU__ zD)}WJzEZs>AL7r>l^=T_L>5^i*eWH{UB;9tlY0;}_k7vtxL5`xBC&atZ!lpK-79vG z-1K5#EZz>5dWTDvdH(V6_HyA)YRP4IJ3%&ti3fC}0=Qf+q#K^-wNg8vgfrmMbUkNZ|upkr~q8 zy22`J7MFQ7=5qbe7U=Pk)GK=z<66t2y7A)f0*iBLg zaNH&gzn{;xVb8)Czht%z9=Q0^9ek*QmLa*+3+^YBH&$^t%#ObNn-cQN1v^tvkW;%y z_3+Jf>Bif^krPOvlE)}_oq>WW+|@-i_11FyFj^~=WZfv>$f(sl$-rhKogRYZg=)8p zla~Xmr?c#Q*g~o7ql1q9sXNp_+BY^0c z#>FZ(yU3W5;0?U^h>y%o%c~LgYrCWrjc3XU2R3d*=R4je`Brn#!5z)=&67I(hb=4X z^VKh_W~SUvk|ZG?`6v*9WX)I-9No4VA=`0JqSX95sOnpk=hbyTIe7@`$gSke_*FH5 z=9AySgUoHSh!$vSgAt=tzQM@L@nhDUuAw-=IfI_oF==gpI+TcBPYo{kiaUdNzJ(|l z1&YatrF&EFqT!E1`ZzYNto!Zt%l^UXK18cX|x{!EI<>8MW>7V#Yi>&22J_(PP zCpbT(?_+mDt$aWqGQ*wI*{5HV@4iStge1L+ac~4=Q;Msb^Oj*7GS0W; z5)yZFfCLiJtZxlt>H+^9 z8xl`W4%Cg~idlYHOQJCUaa)$ae5EqTf&hAA!Wdw-aPzd?O*tlP>aA8@9E~i;=YU-D zWKQKCEc0OE*Rkls7~mLF6)v>=bW!xb;ik}+0*fn!O16&F%Qu*dZcIHz!ME*-B|gJv zZj0X_;J8b&^6*Q1L@RXc?6k%5T(d1x66@fn=U_lZxWyROvqi@P<_dnj@-6{L&K6``R%B?Ux4Qc}l_MREe}1N876c`qqLu7=vj z6w4I|(CeiasXUgEvMn(zFt6>hue66bh%HZ>d`*BB@Lx9r5D@fUo5KTgt&vcgEt*}g z6C&}}wu1ktU%v1t=hPVCCwomkv+5xm9noDQ5BKwf{th-ei1?{fpBn5TzCm3tZD>tB z?x;-<;-=q;>bvdqkfwLSIwu3-)k_ilkY*K!_)l7*up=UWeiq1d>FqlNQa@{+24tV= zqqXV9+Y>S{6)lA5BfmdYsF_JyWGHIfcesT0h6nNdb?wAJF-2S=U4zS>yf9}VeQ}8k za|OIzI}`G5I8sc#a>HwsWS<6(=gLx983V`6gZ@P)5g zb=4PJ1L^*Q={j--HgN^x!3epWvHBnc$|ApkI6LIqO;0F-=m|c)rtAyy4QJ<4N7(t| zN?J9etr6qI6Gw#GJfVURI|)5JmN4vu#-vdRiDptvrh%gHu9nk$CE3tU{|}-JVj3VM z3-&Mp7L(MsFL>o@MT1l6x#j%W2RnBGXdw)!lBOG*&~dBzV6%RqD2`N?BR#5j}#?O z76M+9a9Mxz>go4K!$Ob0#KMYJVKda^&Ccvwcxp%1J-Id^sNeCOj1uvPtbCWIO~lREDoV4A$X=n4<%sf#ZpECwcJn20d;Ko2O;7z zSX0`L;nbu~fw(TzOlIXGtBhuLA}^w~f3x~sCDx4Xh3Ss8;I<4|KGmSFUQW^F{1lEp z$GEClcu1PTLBpgzSZHN)lE@>$P$&QxSNC(AJ#lvD43?8vd{q5WgPwAlVDqdq7;4!hNJqm zO?y#3(tv`F_-ow}t;w=NB#+~e$Pbh*XgtMDucx)%Q)Kn`@5Tk4i*`PES$)X6gggz@ zTF4CegsWaFOwa!&DgdccwEgd>uHflxDY!X3S(4(Y*rW%`-qS1-0e=Y%jU1Ig_kPcB zOga8_HZa$la*YsFy6>B6E=|ur_)?FbihN{vn8SkuMlXPUOcor6E-|{W8~+f4C+If| z!N)R)f>Elm`LZmu7pU8I3QUlN#)rJHtRfX1sHt)}M!j_2ij3X-uK?$e-E_4@MmRjbj z2pcCG-g<9N8k|{a3{5+Nxaa+BO0YM zvSSbVR}NDI%|ASZfX|k4~b6LhC-PC#TCNfxpCs=D8H<$ zxetVGV%f@|bmVrI;xExW?v+`qk0iRmn>Ivq6^lOVVZ^(XATxaFy6xr(r@|*Kl>qLI z`aP|LI&cRm&G2bR;kT#%GRl`Ba{eWQ<K8zOmMAb*ETz&pS?hjS!`q)mLu3LChkz7-CYLrYYoz%vF=c#S;=C zkcuNrwZ5^72qbQWYSphW1jAf*C&!bck}0%A7uZ5c5YI8$M}mogC>(XM0XcB<2*s#T zZT?TWwv*@bDgYP@su216N+cL!3UuK~Y{fM6I7MMkaWk3{T4s=JLBnYr{WS!r; zz&C4#0+9mDKy-VLq(t;OFD3P=`cKeHU}(luo*T(7R6;+HgcAv=#<#C-=O`fuMc{%u zn^Aw!we$Va%X_r&d;#PH!m+Oe+D<|QP=ayA1iL{6q6zPo*jyh<9caMQU*U`1C-@`?U{93IrFake4YbAJLGnR*t?iLyX4qj#N}al@-)dR*inzy>83}f))keRIh8M zrP%p@2-S`U;#j>a_kKfiN)KkwcJU!l+-Ldx_p;lSj!yn!Vnn}?6^uPfbPxVR$ zjTV2PsL1^8V6z-V`NRmM%4=;Y<6N(IzOFNSmN#IvsnyCCQv)2RAc8&^({=)rSm~iy zt6OX;q@lF^?cZR^Q)JkHL@L;yq&90B9A!E8HnOUb8nT6y4^Lr-ID~*u^>_Ec(f5ND zHn3pny4D!!=a5$>@%gXCvZCfzvvq;0G}J37@gXcAr6rfnM1o>sBO{*PSYT@ff(UgnQ7@9r`q7Cs*rKD0EGEtHqp zN3n1ey^Ksq|B|s)H>1UmLzVtiQ6WPPvEcqr2^r^|FmuCyu1Jd+r>`!mCligdO_Y zvV?DfySI0GYv4w3QvWd8t;9GUZR$Aqn0~O{PJ7(=>}z{F&n?!!7Bi9xWLUm(^aBq2 zLKbAbRwMcIi{zzM+$B#eBr6{O>WoPtMiPs<&uID7GX^>+{9rHnIaJm8A;7mjZ=|q)jL&<% z6DF-mTfD;5ndcj*d19QxSsUOe<97fSt)L|Rm5SbithVCjCI8KQ) zuhtzks|XD%e?@^j_$0FUf>MaDs{RMH4$qIL;K&Tvt-1R%i3cMrMLNKbZN4%k;{m|Z zL25d|^`Cwmq!)gz9Wq=TuRlSwRmJr0!G8^LuM6^tiy^G#9y2Lkae`pGZ8~Ri!W-ln@X* zkj+kERiV|WM~)6j^g-8VLC_cFz_ZuB^Q!QlFFAcnvqOJv%a3Fx?j=vR8v0+u=yjeJ zPg^U0o9D0mz?hu_oy61#Mp4j2BZywL)lb?y;{j!oNdL{{|6ur0_$=i@O}qj>3d_=T->!RV}j`SXiPbH5M@;j`RdA`tQ?2R0Na@%aVimVS6` z5s@WFuHI_#SGsJ&|8qIP{yt^Emo5y38F%Cdl98*K`~%kx@yy?EA0RZ9yu{n2HZSvir8!~LG z4kkN`hvwgOKO=#Gt;#R*Uvz2f_e&ic%1S>fbKlqVtavvFoMsshtIse6ng`RqHBS8g zXuV6V*31__v5FSMu&M6T zk?2aWuliuz^~C5{f11V5lY^=7H7Bw+V+$JkcNi;j^nQvC^`FP4j?FVJ0(|%>>kT($ z(0=ZjV*p_pVAFfSKHqs8HcML*Md*Sfypg9IHa`IBrmE=`02js25Ee&!S3d{~?|=K5 z!uRVMnbk;%{dH%;3*w2HRms4u81YRK_!nmN&1(dU^z>%ju|2Q-&u;B-+CMHa7-!;y zfBo8Oex+iHseI6lS4t6fqz;Pvz7Yh-_S%n(Fh5+jgmJ~Li8uIIPfNjgX(3xoKg{h~ z6XO5E+3g2aj2C)OkJg6Yu2whTVsMhX+Yu0t_0H7F;0+$vf0C=@2z_Ah5cB`a`XQ#z z@o5_zG3DB5g-3djygT<4IGj`o0+!-A*67Thr+0IzTfL-k0l**Mwj&9pcrgpkoAO>a zM#15|Hk4Z5G-K{Y8QsZ3qDwQCr`ElP0@s_*mZVdOoNvzFjsJA0vU7;AZ9~aux*_59 zo;LK{MkSb$RH~Y-o6P%-Zwn<045$GakB#M4wD4re`gq7484UL3vuQr2LQc)55(iA9 z43fNb-5sq$D$gbNeF8#31DfxY6B8^8O(l`=%;Q;!_vw=`EX%C5mG@WR1=wte9Itb9 zyvdN!8B(iI?gbDmFBFWmRHaYN5>!biSQ~%Q^<$I<)yQr#`;U*^ZAEVZO&(Fv2cvq7 za#nhbF9gTY9MuLJ&A$&daY!_5xpZFrfxTLY`uyVai^G&!oenx33(5^9W%#y6iF7mc z(HH(l_E;xRusp)^9ZexgwTEL6sylXew-b6*$(~N*+MS)|#obaZlh0?YyPXSX>Xk^| zIh!xWM$;Sb*gU^1mqaVf4;f~(_tG7bb-h)tNm^Ie z2xS`DwrK7?wWnG2+M`7P_JeGDD)+S<(_@ifdT26~Zd2@ma6NGT`K#2!C64GzA$fzi zYl?RRk%60HTujn87Pg)-Whg9bMR(I~ftx2&PHuFwe>;F~d4k92$gNHy{CV_m1~&U3 zAsNgFnUelNt-&lER~rw{JwLbAyDDw=_kTI3T?Mg*488cx{S9s!F1k;Vzr6NF3EbpI zz=T$HNR_f3b$%)#k*0C=uZKoTH9*cHU*C}Y*#9+uhi<}gZ7e4DQ$-_@je8#D+IpVb z?PwRfGkIA7=BZ~IXue};=1H;7+zAX9M0&%1a1h)BXWO{$v}U zdTLe=!;rXH2MObw3|Uk{6%gzh34RKP-T7r?snB;z2{@7)Z=QFU+iu1HU;wT`TgHWw zVL@WjZy-{Og13jEMut?_+3hc?A6G)!8rxGe0{IR8#pHR+T=ls+-tZ>ZMep~*g$-lB zsZQU0Vfj#Y7Vbns$e1Z=?7`Rg2Q7xB17XzEZImyTr^j6#s&D5e@F#lZp!(J_0P=S% zbn=bJ+9E>g+NUo_NN&lrpds9IjmL{fIr5}4?2dMii5}qge|``ABlz(9-S867P~*S) zVZ?dwGF)qN@1C@SpMmdOops4MTFK9YxB!MrW8DW^Jw{^<(Tf8 zgq$!O;H9_NYk2&b;oUWIa583+aTKLK3p7V>mXLs?776V8#dk_~k#Db9>WU++NXOnp zpW&Oo35Tw1RKWR`cgZBlYD#4(cW#{E2grDlkJ~?=d+;FLu&C*G{7!<7rm6ky^Aa@s zriJ{4su%Fz(mqr!uP!e+mjO*nvC!l+PDi$&^7zHU9RQNHUCe5%nYTLSFS1vdCo|_0 zs!#N-?@Ooj;+A(2HYc;XQXu+e!s!Jx(1W~P=Hi3 zi4A{pS+4J`BU0nNJ|ACrJM#4(6MW2M$-HJbMYfl71;eL14{L=+&#CC~O|up~k)lay z;(Hmhy)qRQ^u!My7XvGYe{_s$@53|BC-yDPBJTG>4GuGZ3jRE0`tB@IDiN3s;4geP zWACAYX3QH1#nteuk#j6zH0>89r%@!Gm-;u)`U~DDT^BEu%Nw6=%y9ik_#J08Qh31_ zt!YLz%bLooTJZ4#nfl&HVHVZw>3=w$8waOy|03FB?CaRdy70;XU{&*D(LH8vDkoq6 z&Kx=U+H2UJpKN=Dcyj1PYTgPVAil)OJsDJZ;x^X|^;8#W@ukb?^DM$LM$WyGVU#qE z9P~C5ZB%Jgbm_U_po+*5%$g#@zo}&WIGnQrIUn0B-C#k~g|VOn;3~D_A%=#ToF3X& zZ5OwEKO(PMdg!oGVkXF6=l>r~R~eR7w?v7TM(OVEZt0fpZjdgK?vPHUI|Za0lx`%Y zQ@Xpm?g760Jp6=n*!%36J+o%bnm_Ma=cgq9{m^mScwv_gb6iyh$vM?qs#eODHxl{3(U6%r-4Q&r87dT-&Uei(3viHrrTN)wPFDa8UdQ;^o?|_L+vyWj9u8g#l&}KL zPbp+)XA>*Q+1(0y=iO1tTHJ&DG&?@gNx ztKtullPD1fMvuyK7pJzGG0{?0PD#^Lx=rp&YxeT=p_2Pa$*tetg;sCDa`3p@FV6q|eI1sO5d3-WmU4SyC~&wj`9Db14&W%UDiOVC17I^-C3Z6d1! zB_4x8&3|A=yDnG1!Cn&Z8dKXfl8FYZ17|6k;#=X3nXInJW_&R3v^W+IrHHZdZTf}A zr$)Zdd%;V^d+sTFcLjr!`{;V;u>S^wlC?Q`ALZ7);0?BU#4o-v1L%2`%+kG4Wl9nf2ZBdR=Pxu6lE37bB(kWp5*RPd_)X@wtf?Kn z-$Okp^(!&@@9DH^_EuN`{0p%WE`6oReU(xJIL6Q&C~Qr zk!`v>zhUf3f*qD=Pow&X+4H>R>j4|BiqUVmO2MSzJ?Ey)g8<=IqXdT#9~|&exF)~W zX-9WWCGO4?%^};~h{SdNlL2;5o^_GEi<|2M%$8d2x95m?l{r#Pdb{BsIC>PW!?q{m972 z6#SaN1R`oZc3m<+!`7qf7@REqOm2bOk1lgl)pG7k#r-}#VJJ8wsTaDC%V?1o+xiI0 zV5U+HLvpSOFS_!Qh{!xud;)$4YOHCK=oqJCY2?Qq`|QiV0U%wJl{amJFdogBYO3X( zj%PkziIPGV+ICl=9W|Slfdy``0J4b0-|xLUJWKDv#;FH@9rw{-rgw_cQieiTCkV7) zuZ=4IUV0J-|NidGbmoOwxMk`#2Up)MZ2awMI-4m_Maoe}anEI19P>Truk8nFyW8)W zu+ds<7025WH<{mc9LhRx5hVU_N}CN9(C#nr2R+FMC=vaZ3=x|qWvHKRUp2`=!|BQL z((2*#)$ix@@ksafZojM2l$L*PE-099^YMAMk6c6i{rZ74fLxg_F0EdDW#h&Hf0QlI;f~ zn|7E-I9LgA5tddPb&uaqojB)zXGJzyW+5g1BvP<(Xc-;qxN9|G>QA$)nGUD^q#qkh znGvnvp!Pt9RSp&sGFde|CAqUlf(ms#L`c739F%yx2!-qr`g}6){wOf6KuP|Z&pW~@ zDlbi3G(2N&yL}Q=2+%$u)mGWlyVp9>k3iw8pPQXnb8i@1bN8)FnHyo%2$if3zCZqw zsB-c~A|zY+yIAd~Z?%N1V}B7V0o;#rXi24+afFOq#y4A8wXG!|Wi_R9e%BysKtt6E zrEycTyU;`(vyy$j`9ilf{`Cr-?2~9gIjC4vo7sB!p!Il%7Nhg!IJJ|2!ll*C9Mu?{ zLV4?*zM4601GPFmQ<-%=o7y$wW!v4m?=1!o8PzhJbK`Cy*m5fLK03`#o5&%*Ah}-6 zf)TeZ_4h{vE%#NT(+(KHi7YLfFD~J2dgt2(~X= zQT&^J@&*G)svF8Qff_Fb*I;Di4&(_+($6-qy0Adm{xg{WjI^{ii(1Aun1;Mrd1c z-jJxF zbAFL`dYB`Q2?>A@zhhbFSQfbi;_t2su*BHuPJ^pcTAs=(3_reB)3#sgEI#~?68gLN zF$X(gH{`1BD-OKc@6&KZPi70u!7GZM-tqq+sw%pTW=`|*DrcgnX_`kFX@`5cPebF{ zlMq5w2^aq|=C_aguAv7VeL&83_&Em3`slxo<%~S@6IL6)qAsZ_zxGaZTLLf7zY5fe z^C!KH$Kq~F*n@7qp15Xj2iyfG!=Pf10q-oA3b}P8XtbO*E9J@SqGjy0qVrF9<%QgR z5qoHVbTZwjZzXcy0~BbA%dAQ0twVtu^W9k0N!3g5)}oe7>v7hA0X=+^l)f~2b31M;K{*s?H223oF1pqfg(T{6Koq}!Pr@2w%jZ&>uE8&kwTj7mZ|J$eV_iUgwtaqn zuC{Ow0rO%iLP!wy=Fo%Y`36kvhr;~b!V*p(3#ffPVNCpb4;OnauAOE*?=@TnE z^y1ceaHC(p@P1FOylIx&Punk#up$QTHI6W|j>U>58(5ooFo)&g+EH=Snh7P5A4=L5 zz}3BC2I2GFiD)YDx+%qfu63ei_f&}b#=7Rv@974X_?%n7r{D^}Vi3pAup3gXK=Bjy zC`75##S_Q=Z*<)iNr?D&*Pig7Wpk3!{fVyE;s7LX;RlpRt8>j=i~Y~cxIh)#MbDqT zrwR)5K{1%5LM9V*EF>(t<9>KXmylziHw|7-P22#QacUy8n3=rjB7`{4F@pm+O@AkOqW z8wXY+St`)>g+&Gl>mV>t0=dy8d?vhm4w*RrLTWUwRR(xqr4H2Y3{L0HHBV zOyKO%BY3^FfuHx28V9d-QGaJi31O6UhSH<;Kr5@+U~-j1B`IHpV(6W$3A>OLK=<@( z6RF#zQrZ2MNBq{}qbT_5yEv4TxfF9XLhf`{L&pG~+0A;FXTx=We}9LJS)LIdJyD0r zSMWjPHjCYX_i*87Boqlh1^`2MM#}~}yXwjzdwikWtGXf_yt0^FQL)*J)(|PaZ>nH! z1RaqZ{+J>C$hGCFT=b19a#C66D!V`JLlN8nbmO&!(tUD5>x2x#bd3rs-c20(belQa zbdwINj7(U|xGMLz=GBRHn?=dK*?FXxELd8d{^dKH97i!`%mK!%sqMDQx-i$amlk+g zr8AlwBhBXO(Kbx*4r(d?$LPIeLG^vu*0;jo@LEdZgUOG{zWL@IkC$gh$E77b2xb0=$Z< z?@km0?<+|6u==fc548outa6HhUP9Sn+@maw8IprnciVu*t<>9@$EUzWthYEqO888Z zeR0sy{-h(A>e}($ZKHd9hO1@GRd*GsZ+zyDfbCCEj{=ijN458`<^rZZnc5W1z3&3u zoDLmQRSz9f^&VK%Hz=-Dic3n3^t*=&=b zU^*b(sMMf#C=Bzi15Se)?SR|FKk{G|OO<<=>jqYL0OS8!0I%%`9>}kXMUD!ClGJRc zl#M7I_UcZGuB>wZbb;Jsc&Bl9!eeFfU5nb(xj;*4B2h+JUl5y)=iH@M*=%yha7xl1 zW?IXkApR$&gaea`7RPS{74`a28z&I1CFYkty%zGjXmrXGsWl-%o%S8hgcPa=l z(^EC~&4i{3?5}m&8PsIKHul}2avA_QY0*RIAdR*Tcyzh=OeD>q^@;C-x$A+~hQHY_ zk_Z-^f$kXwD#rfK2u2`T#E;dp9u)1(X7O-yivF?pl@3F!h~r%6=$`f%ioHO$zDOsC%4UCW zw)`_vP0=o469f&wB}P)chyzhFd`q%!rnImK1zW7JqhC*eJY!}1`mU~v#S^7+DWksS zMr&k##(>E-^B>=)FMFlA<_LEZj+ig|wkguJf^*8k=U1_nTr%YHATO6DonNF!b$4sl zV>|^0)_43`BekOyfKZ%XVbepf_7_67VtJasavK67}?3Qw{ap(2D-eU!FmQv-_(MynH z%Ng>TU3R2hz(LuirC7=o*2B@;52Tc8Xxt~T>ej9id%jf0)S|@qNJ2zXOdao<865d0 zUUUvrG&5Ihpv%wg`zO9$spnX_R%A}#T_3S3NbCT(^Jhf=mzKo5;-xzFIEG;s`MF6H zX}23*iqSJ7O4UdS;d)66~v5M6E3JI9N zr3*UCB#9*~cKu2g!wDxesnb$zMCN6uB-DI75=9JN*CA~Bv%OOP z$7wvk8*mqIsC0~DEUJkw%5rT;y>}ktv>RJ!c-K^~aYv;vQd%7~#{62skfmg{80f7* zkJ)z7E_Y|;NB)s)6ODd}E;~;u@&KrJcROMrOj!S*juHw3?vGYkwV4UIJQ}5i6H+%< z-Kl7~UzOsZY3(*CwW!`qH+L>i>wGBbc`I$Zxr3#e;oL+PTTw3Y(|_{6XIJ-|!?avJ zPSJIT$c9o~`}|&?Q$XlTe#R6oK39CT+&k3lAHRK-#{VID=Zk35gG5MJ8~}O?9YEYB z+D8L0$2$}BnxLNilB0s{W*8GpzvxDk?2uevKmoDxTaKL=3D61I&H$2^b=0_(3y8pB zC#Z^>czAO0r>_sRJgC@o^uUPq#VoQsA+rPoHt^7An=bnJ&jf;MB8i%c$o7{f+#PzL zpgiY>xZ1wM)V!Cw2)G~gHn2H1azSSE%22u8!`nUVMudlOD(_O&IR-G9c+(bDw0Q%K zzehF6=~e%n?X26Gfzm{K0!XoZ;zO7GHCjZGZV&gqCP?N25c;lK5@R4|5)>57(MlU3 zQoK6-jmbLLQ(&QCZu*|H#V$Vr2CV$0%$+Kfxt1ls5<%njVKF;8&#+)-`iQw+13)BYf3cpSQr*1_ZH8w%$uU7s9DG)G zVNwF~0FPGYly*4r4^!6V0I$ohk@Xh+vDcQNPpCo}CMmUeGve1M&q*1(zPYD~7Dna} zu+;PJ7o@cW&VHmIiX0r%LEAYr?sx}p^=THkJwT@jFfn`uVthkswQdSoB?*;w$_R*z z!_u{juvql;vOKuGpa2*IjpOIf96HHp)#2Vzb1W~&9bt^Cipk-Hz!JN-(eqtfdFet* zm`6l?X|p)p`|6Oa1=CD#${7K>q0{3EM-QWTIi#XF%;u40^Hg>0am}&$E}ek`rwp!M z!oJri*y=?9WH@&jTm|d24i^pW@OEXCYXN3!V|M##T1>rOJ!++@EQE=59RYqIwOGmq zVd~pHG9dlM8Vd%6rawe@bf5D51M#cp)|K|VFSNZ2D>%uyP-Ka(j(v65{2daYbz0H{Z z)!*l2Rmc=fhrDr&mOsR72o~v`dHzfV`rBeVuzKr6qiuAZGq)^qT3Rez-oB7mYsfF> z%g;|91fNu%`h$AFE2CRj79T`iE}Z}H_35SN7bc3>I3EZcFixDGZo|OP$vx#DI{R)q zn8!;JAuYCs@yY16eX@7TFU}7Pv`6-;(8sG#;xsZPfG#GW^LZ&MKtOL7`X|C8gPol4 z*3UiCK*;V%U#{H+35WW!^oX)}>1GOSRnBriaHW!CmJ5RM;iA=4H(y}K>M0WZ*vS;=!6?ro6}xqf>*yFq`k!ED41-hP_ULmHjr_Mkfl3bJQN=sMgDaI z--A5lwKAtgtjDF@_~bZ7(1LnVRTC%_X@hz()X`9L=h038IjH$ZZIMkNt%HVkQnYqQ zQQg0hZ!~ukE6ACNwCT6IFETBT{^RrrqX(o$n*xm)-WTFiNWch->~U@T#J|#6#4=g3 z{D7ZMiJeZh+zZ?1^NI?oa1OGPvnc+#MWUS$P@;xg@z21S*xleon71WFFI?FIf?eO9Ki}{7>;wNJbQ2S2fL(8^d&zE=d;A$sUt&nv!*?|z#Aqlm zI4ClTBU~DY*08KT@hy?8RCKN^KEHE+Y>O?yo_{+jLfOI)%|B}&XAJ4^MMgsE$%)>?Pjg(wi|&hkp*`hNxoyPRiXY4QIP zl9Ke>lQ1A>`8(Kp44e-6 zMY0kLqE8(=?AQj`m=gkUp-55%#1<5AwQ7@!a;fH);lfn_Rkn#By@q}{NXz##FU-w< zQZ)n+B1+}oEr%mz7AmjGnpxGf^=Bw>hLhVg&~{zM57>)Lm==YpUun0dt$i{HXU9>8Xi5@QnWGA=PPW>w`&&8QVd!_A4y z_LgBpQvhjOh#8F@$zWRzFJ(0ylO2gnM%l$bpvit{|GRGQ*BXI%cc1byp^pD__#{!O z8GQ=TR1%V?SK%G#N+K%@7J;hgbEVplKfxL73Tb@bJZoxiGErC!3|=jQ!c(uYbQdr<(wfFlky1B4*ur83>?(Z&6=W>rx|mdL8qX) z)8Ba=z6&HncPP}<)F088x;1v*3(xb1`AqYwpbi`QvRH3?Ye?TEXts(3oJkbQmz~oy z*N804$g(d#J+B-iYRm|y?z3JoMZt9=mN&no0{gi&$`Nf7$4U~1k2iMj!NUo>(YRe6lC~^D)ad|Qo`ugd z40u=jF|F5HLR|-|pK5%F)G4LiZtir*CY1Iw2zqY~x0WWj9kdoAG5d5|; zi!Puj2M{1nw*W4A64{Yoa5OpbvHaxsn}cK3IbLz!f_VFUrYc^tT?M#|&8)ohQuWV{vYg+P9qONV6^S5DZXdUL7nN z>`<0L>JQ5E8Jum~jFlJ_FMyU|+)07uwTbS#B6$F02hkZBCLYlQ?yG$wCe#UrWhk~I zsFTkxazEOG^qQ~PH1Ucq#21L*Jn!N3h*9FdA8Mrxy_=};$RC}mYHvjT0`j=u34K1` z9=x@DGW!YLGxoDd9SA{+iGDf&>Hi(Te-JrX9Gj2=Ugt7y(Yq=$=P9l*79V)M1~dhK zK+8tlxG1oV%_6J1Kn!^!vjM3l+2^Gnm&3cR+xYA357aye9qU9!VyBk126m&1bg?kv zMue$v=#HO|EKnL4^y%km6DSzj`2-8Djklj>!qI{E4&{AL{R<+(5F+QB*R@H<&cL3s zM?^GZ@PWKn+Hbn_cd3QtEo9Y|YuF*E<9mybTTU^W%V{7TG83suten{GQYM{lmDj>Qx-0)R`9= zeus&BZO*G+tFC0W;cobm?ka+1Zdsr6h|a7LNw>^g*JFkDtXQ%c1aN@l{On8V->Z_ydYUPyXnt@7TG_Il@zSrB-GgR2m9iB3ZUC%XH3wqwi)Vtra zdMYV7DsN15o&h0a4C11z5~m1-!;`b2e~+b3Y-1PJ{wej*Y-{m3rL-|VP}cqN(JUz@ z#r-<-oOhXbv*rAVKM9`wiq#x6ttz)kTVIKJJ2M^mUa3a}tbbi|N2{j7!g95Ntpm3d zCsQkLElj@fTr_68#$*^5-06jl0S1emQKe6xqyM8CpZGg4c4-v(Q7Z1&Hz8dVPVpO^We z6JWHUiGjC*LwEc{O*M6a@eVs+E*5Co%f*r8N>p>Js>;z@1`B-+vC%1oYGgdehoz?2 zVhi!HDk{Htrt)sO9dax4pv4bXZ!aJ!y%J*9KwE0`t;sUuf*4$gU#n1&>8Y19xvVBL zHQ(j5Il~dV+bmW^@l-pc9F_6?q3p4Ng+`|m!gBOwEc@B2?9lZ#bB)+g5aRSSHJ*~Y zykXGCMlJNlje+M&dB3M9l4?}Cx+2OTG$u3ifhdXTf+wIlSlN(f^XYt0|Gf-L=TI& zwZt3-?f0B~Bxspp;jdf&C=%NALH?x+C7n1+-OP44q!P_IZOqkg1r8WfyC}Mu> z9OI{iGy*!r=5Wkp*m-gNkM!6#r~@gFqw;zpOkP$92C+q4d1#eA@ z6;Ss_*kRqaA)lbqEHG4B3gROnozz5beQy-rZ-w`jIy-~n^%kK8?;?(t2UX=nkiKL@d1V+ zx~BFTF@^wTMT9RlZdZRwi5DNn9~nHoXWbha(?4D5NW2!~-k{SeQX&;KTP_-!%E`G^ zLsz$Sb?Qd}N#|QY;TH}f@6Wk2b9Z1&|3b?VcCPi`ZH`7$lzk9A`_w=~dsRn-uD1|#Hc99x8?Xw!uAh4&9G?k8NRRMRHeB&r@-JavBl;Qd5g(I zW5JTNWa9O@j;2wC&bVzf3D^-qbtY0gzEjJ11c4Dpj9V)gjJQ6qZHH^4~8_Lw1;unw~%KOmgT}D&} zM}}_G)w;6OB>NLT_MH$|zX>E_01m~?HP?~^+y;Z$q@DY4y7QM08RuJxOng0ORiv*% zNnqemuqP5wkxmxIe|-*PGYP_393UBZl%-0c(eeVE-u5~Q79A6_5w(eGBo}bj)*GmH zKwq^d_8)MRUp)4cKlxFdL{*S)f`IL8%Wfz7j*QLAX$vDq(in7S(cr?0>hEGN3{Qf2YetVuE`*%Ropm<<_8x)m|YAlzz^a)e%BO3v-XPD$Dyr2j&NUd zjJT!tuUA%joo*yYqGV}t3k4Ri0=BLOZDV>qmr}G@D|&BGhM$*Wl9yj#PR`RfM8jAv z(L%$9L|*&q5eGozD6=`$5$fkUE_ZdGP27pJzaYZr^hZGrBH=>3CN~H`UVD=X+(lek z++r#rl*yX4u6@CRDIZ`%XEK0=H6r={hAMr&iVz&1T+iQ%?rhw%^jw%M_x|AuC>)(= zH5@UMvA&kQ!`hKNaoMGi?PkNzezUxrRLGdI{-d;J+=QBH^wxyfo(iINc(7)yf+@qv zxXsJ$K4tVJ{%oSJPiPgA;>+zE1qMf-bmF-{175?g5^Qe9p?!5VoYUcMPbd-#7!1B3En zduHh^Zlf|c6NaEbWVF6$+}|CB)x>>)pl^JftJyemU+j8AkCTTgtqaGXw}|;`SBLd7 zi*f&<2!z5tz2$-2$$pxyCu|%~jm$VmAnV7t#K#}Y_~iZ(ZwuICj`o$kL3!daN6Ps5 z%w%1usxKSr2EC!R#MyY@Bdr<>*S)q3HVcfC{Lw+@)phTxoMK8VkkhQqDf6a3ewrM` zeL-#L6|#T)^L+0Z8uN3+AzhrOS5eW`VGU-MbcKZ}EV0p6foC{mfeIfZP9H}VnXb2t8GX13*(g=gCDz$zc73xO!ESZBKQ6G>-&8mtiD1j zbJ?Gdkd8kwlfIs7Wrpt=g|tSRzkNp+N@8w7kV@m&moO zf8*}x*$WlV{ZC(&0uCKZgUZF(B}Fu!7Fvr{C;}vox8eOQE>YRy`)A}}e^?--$nK~N zM=$n$2ryg|E$KGt=jPt0Si?V;k#45aWEB9tb`}yNqxhTNPy5JV;TK~~F4i&qNt`S? zqRgEg9-m!b%qvpWGNWU6hW&3xg2`X5-h=r*CE0vhM%Eufp;i<^+Yb9_SL|}2_sEK0 z0jso943e9!ZQA9OCa!>lUq^*y;QB&deOogy=!v625&w2AS%?^#>3?(Bn&{LBb8W!1 zqu(TB*YSKBZ^7*)zhYX{i%99iMGc{Q`LN8?;76EY6=QYlrqEL`T4F-5)186ouA2## z-2I)rA{c-ZFA2bq5H-*y#U8SLM1_10iMC?y8vEg|XH98ooWHmT?rS{bhY121lm?}V zmt55ZQyva5S)jzt3y5qAT(MjHk!5B=SX6BP&lgOC_|%rREoUy%Y~OW&IuIzAiD*fz zAd0?OC}Zp6W3 zPi8%^wZ5v$C7g4m<2HQ$E6dx9RRHHR`Hx0w9IXJ= zRi{GRs~tZ6YghwM`n9I?_5me0J6qK_tykslZ&8wD=c4t!HZ8D9DLV6fD3h7&`p za;ogdD*1=?rWHQ+--fj!=lX1`cpmCzWLyZJVjKSk{WMU1#z<@}mcf~Rg|{m~dcoL{sM*~PHTa0pe}|o|f73whEW9k1lfaFkOXAUl!Ln~B;=Dg!ZKcvAFq=lanG?Q(%p95n+$4;ocF;ED? zN+Z*>kVScwgANom+`SOS<1yh_tyRk%);V{rj?&SIXEx=*BVw2z-kT;EWoMMu2j0PJvqnRE^6C|E>Jhl{UQZKp5y{z%{ z^?S6ws<&wB8@E3?%gw<(9>I#xy?9FlLKB26f4efrkt3Nm%aqoS8t6edMNeZ}z(xNZ zl$oe6NN6dgYivsI6+;6VhdxjPldJna!P+Q zbEEY(af$_Nc(Y$zG)<26f1~j;F?CM&okL{@`%&|W7Ne}KAH7-t%VN+idgOP}#;G6U zs+&a%Q?LCm6=L#_8T6uZJfb&Gzvi$qv|p=Eb>gNa)>{zcW;ZaHK7ciHSkOU|+uh#RVI(&2=`p-rp_H z(OU#s69di*&w}}YvS%>$s1S5U+SFq^;^q!<*nICGWqL`mHHkF!_WJM0nyj0TP^uco z`ycPR=UpZ^1?iIOQ=m*!bxgYY>h*lCLUQHM+pan$h656}gdD$LWv;#@^Fr1TH3OK} z&Qi)eCJ&#=yt@q0L4mW=q=Pd+cdAjyD)mWD1S@dqs|S;niV0^EGcdHL>YVMMqVR5t zbtvpJ=47}M46#%=`Mds@Ze4wwWdJ-AD!vorul1qx*xuuTW%0FjLtkbv@%^F<-fX=d zxSmL1iurN5+hM?PBX`KlFi7BM7!2kU(n|N4 zOs*8eg}P{W{b9nZzjJr-cB3DrzqLU!ur?hN;mtKN+{sa&)wDZ$bidDf+sb*A6Srbd zmoH8<+v!NtBXoQ{B7T(f{PAqGmvNdl0Hj1M>_=w=;uIoQhsaOhXiNGPh>)ZyY&B(2 z$?xwc=s2|VeX#ZmoZ##C1%vSV_*88|{{3^n*V84^ivU~&FmI;^|0?%aZljB ztEjoG>D$1()8%wXIYjh+O3t#kg$GSfP=0$iUmV2s@)4LZ{pV^*8mU}lO0$m#5hC*u zt>(#u+U$Ggc4^qh-XkH8W&!^2E(RR^K`gs;Ktt9y8V1=BIeT-cX~Qr5JFnFZyd!n6 z^vk1Qv)Y5utYTIfc@i8fnHdg$_^#m>zvK3ENJMT;5Y-vK-inF;^pxnrVIU6Iq!u|i zm{huW3Uwbiz>RYu4A&$t6;^&sb0pyLvDr(^^{PFpk2&O1i^_C{C&WQ!5?7@?C&#{j z{S=j6GQ3tOLZZCXlL!||2oIr4L)7Hh(~byQJzg&a0MS5a(i|--si8|KHpJ@v1e?J@CbS*q z?CHv$zpjDyQDK(k#9AY5{GF>tFk*K1z>t6KlCa`GPH}0#V8nJF(D)uU{WXv41W8Lb>k+`& z2zWOXP}|^csgeq{$$5UQe(q#R!SXJPMM#G74+Rh|d=^$G#klr=XF-MB6f??=p+`jp zM6>EZBLjE63d*yLBjAz;w1QqkBE>AQglz8V4z!A#_>H>SN&W=+aHqfW<4|4dw4N+! zTVGqZGwwRfBQgH$#c?-=Oni}E^UUC0k(uYd+{kNCJ>Ky%S)WyjlQ*Oy!m7wbi=t0r zS{Tgqu|}}w%RU|*_bdwvFGaj)@fqR54SI@58y&`_X`N7uANrMOR%ajrr@PGrb9pBk z>d`UR$4-09px0FP?++csg$Sq(FvBgVgt1$>;@|NL+GU2qE^6v#10nSV zek<=JforDg9ULej!BY}0EI}D!4jh+~gt(itO)%L(YdVyJQVB5yco5Ko3}=$0B9Grk zE)W*0o+9xPyMY%yz&0@@d1Rx#mO|z4W9y;|F8;@q+AS+asblMvVm+)=#*w3@Cv2Cw zlcU3WmNS2|wjq7`r2#Xhf3~nG@q9kfRs_q18OacqnomTA$(nq4TODSg7Y5UOj&$+ArmWLL%fmg>7}*tqtNv?Wju(8nR^Pr_j&9C zgP$h>@HNkftG?e=8C`C3p&${CZ;<{&EP0aHX6poG#sM#DI)n|BR{15i*2O;IM(Qp% zIZ`8?3A#^r;l7Wvw>p!gb+?!~7+uiF+;#e`t_-O6J?o6apE6N$r+^1Vy@BATAp^t z=B7Mzitymb83&^Q|HK5!jY1K;IUGf_WU72~6x4)OQsb64`1LObvgm63-Q%XbBe5} zW*z13-7Ur?m+$xuGb}rWX$pN!NRm8H;X|cpv4HdT3_p+}WvWg|fqL(+BTUe~c-AOk zxtP9hT(^nuTM8yl(^C8Uq^I=vic4u=Ob98pU*NBX)BA)d#ch_Gt%QtN)QoF{k>e^c z;OVlp$l3CL&hpsN+^>v6PF|5UCkn-8L*WLy5k|sB%k613*mOxTKOYU3Dl>OYm#Y(d zvc1q=;%pM|^>kBfYCBOdV@Pr^L+q5$9@6%5lsRHvdjy(4@s ztuK479(bvi4|eYSX_vc<)3Y|EKOA65D59_bJgsEsPr%q7fLXGKxDWhjO#7L6%I5TS z^_K-=a*={H4?>&Qb?gjuu-W?hE3DIqn#}8Jgk)a$Yjn#EYmXK*LPjctRuNEb`1?1` z(JhLzmlOubh4E>Re7};>MwHr+jE34~)25-Jll)d_ezAwY!^@&> z!rCkQOG3uYbXB4fXH`A@b~^KdP_+~|4vZCMMr74ne%cM#)@`3~w??k9{);>+&%n2t z94)8sTa2Q}Dvjdv6{_qhxvonrfPLgbR`u-8YhXffSdY!!aLsKPb@@wjTQc&6wGTaY z*S^AZJYY<`&5h+x+SA9&JiLX1uNp6@myjM1*bRD8@HEnAZ;agTc?3A;!~GFy<)Y%h zbk9HRBm@#dz^?McIx}fO7LfeKNqx^b;SShpF<`@=;hA}?Wj%@&_^B#^P|DC1qHr_5 z`}#xCbDZvpr$ujGS2>@^;I65btmX&P>^-hS<+GW8J-;rIpB_|3=^_zSD2>kV>(Vc6yR(MvGd+{Ob zd&W^~Pr)jgO&p5Q+3Y7sGxOh>w9DuoUBR4uon2xe>XfP&sN3X&q4*%m*mp&M-=QS= zy!vDQQ`otyMG+rks&=0&$l`W=y|!qE&B}f+A=cm;+@Wm%(H?_pQ5kkvjPT>LJimbd zr66TAfn+{o<3zNbq-WrCtlct!VVY}gi>$9XGyfW<)H!^QtwzDOuoPTQLz3BO_@NK7N&M!V;Ii(X;_Xm*OOAfsl9mWAX! zU=-^>WG%p(Xt$y^zNb6!1dSI{%o)DpYAjQ;Ea>!a=X+Y+DJ&B)GB1Eio0!8Q;G$ZT zZIe5njxA29a5y1oz$0fz9Gi7)@D=Y~R6%SRzNoqMg0u%!(`TP4v~yGJO%PWDpCC;I zDy}doO4L96;di*4ll^i-?Y~TcFKm&=;6G}kdG}nWy6slLnu+iu{^8WOV6GQw{5N(v z*}T7Wn12R6cJmUKGqPQ3Ll-O)aNNWc{H{QI$KUWbFF3rkFVsg>kRWobjd`dUhY2>X z_Ew1mgo(8wxOXEG@$Yse437d*YxLe11v6?j?ovWT=aCBy7JWU~0xsOPJa#|3mk5ID zo0p`mLMrtgi5|1wCr9+v;AQ$x?g91#LQ}1-DrXuo1$TYtl~uOCM01UJI|wf^GerBB zW{JMq>(9~9jNLL0vlHPpao}lY4_^d+^OebJ@tr5u4g?bLY!rX@O@zOnxqtSum{3^( z&$2c&!s{?O5xT$00dHO|{*B{S;3w zT0qRGw%88H5BX8RA@&=1TbaXD2(NMHu11;bdQefcUFC#&h>y-{uv-Yk^;D4V1Qg&R zXP^I=iI>JV;Lf>9?k1lp{D?2f{8<%{03N5inDb2ZFzS>C?Ti9n%Tvjk6nS)%ptRyFC-BJ^wgNQX$rDp~yWwE15q=#EZ03X=Wz`5{6e#qd^=h+Q zXV!laB=P5j3*_u|WbG5Vd(V?M4DD8>2a$6Iap87XNUq*=Xw0*c!TLG;ThDsctdIc| z94t%U^<{m(v?hM6foCjPG{cWiJ;)RXbHmWyS4Y5QDQCVOQPj!#8j2tj_`4@?(ERHV z$T7I^8PgJC%77ahl6DjC{D zE=jB>I%>bKMqwP{y9tXCEHZQ0Mi4EmnAWz4C*>_YB9L>8k@j~SwWJlC& zsXu?+XsywUdMxB26oD?yQ565tNRyB_CIHeqj-Fq0!v>N26nZKjMi|vb7Kc?(--6%i zJxQu&jM11u#5X^eR?#pYEsX!$(u@i+!|&tKgrbO62%o~dLjxb_D@-4=hccnPIb@~F(A$8ItmO9CJ~xji|Xj@9Xvk^=E9Lc5A+j42dSpGqXxZq0tdEs zD5I$|q$DoFC3d?|(iTMEOd%v#T;UReGPq0_9lb%?D z`Lwoz`4-74Xl=yc9ILqQ!B6|j==viBdx5Fo6GO91ioiAjm^<_O&Bu|dHqruj zggB~RI~YtLs4A8Bqnz6q`!YPbWmO9cLOMr5z7JX(yPgUSW|Jt4d03QPJFqtXw zLKZVxg=EpFe@dIAL@QftNHkBE2=?s(F=6W}enc?f#y1o_OS*Ka>c%CnnDk_WC3&9L zU_ZgAXKqz8()#~A(cQ~|>>?;bh++3|<;m9}1Ef83dtFV*44QDXM z^V7SCS`8Z#-1-ISmHm-c8B}`)UxFdaU37qn_u6V@fCIt z;$kAqAMbmr;_iBC(C&U|HjKQVrs(g`m2Yf}<3<31tgXJ!Wj+emn<)6%&dv`_KhKIh z+Zq|z^R=fwLesiZX)0oN&?U;^uxl`k(8O8W=fV3roer{COH=$&EncHA7?YhB)AXO> ztu0Dx+HOaZ+B2o?51Pw@`?JP*9KSK+>l6O`0t2@H1+d>1qzQc_g~tc{XAUB8?RQQF zE~)oC=QJV4$QEfpHe>79Q9? z^Jyt}2)zH6zfVm4m-3Fk1g&W$l6<;B(&kn{kRs8#&E9x$nzPc>fTL1vnM29lFe4A$ zCMydnn1KoRAwgT3FenYhE^L>l`08jW-rF?&dcPi>5(%kpL zX%?07wjjoCM&OLs$I=YB|e^+Ilmvq4-C(J`$Ulif*xoKi#KG@lBK+ss{DjoSOQ!%=(m#+6k zA1m?js5dxcF^tE8vr0Rr?9ylJ^w22(f{C41t04s0;0XReTI+uPkGGZO#}q}^4>9I7 zf1ZTuyk`3u^^%W1b*x;r7JbE}#<;GODyfJkm$ZmH8I5j7ii&zdP#@-YO><#f1;|+K zp&;SeFeIT9>U|WiU~3np(Y-c27=yZ6nd%b%F5BH=Sasvi++Vv3dmX+ zMG>2P(~RG9I7L|t6rZ}`AY3Ruci!xEqj@;pr!%IH{Ew)wj*9C2zGlV&h7gAC?hsJA z2axWTE@`B@LqH^@yOHh?X^<`n=`Lvzr1QOezQ48Je`XD9%^L39`#k44XP>?InTi)< zwDz@CVt4P86n-b3`RFtCtJ2m~eb?TS+qOZOdRnnH!!L9w&tOH&u*o9A}**5Rv9*txblenNv)uA^9XSw1ej1v^Pw8$8kk#fFw`}kB>hqi3DTF#AG8kx17_{Vr29~vLtwaGtW<85G^pEbTbIluUWvhBq5g4Vg|(Jt#w>Ze-KP&qh}9gtx)V9?bz zH|869;R1J76sJsK-|1Sr^BQ}bR<%BVVY(QKoXZz_O--tJcgQ3~f^K@3C)k!M1}hK9 zomH1>OgP%Hrt#+f)v zxaZ1tF?V;zon$>Q0{ZDHMDc=m=l5@(3>mIM;PfGtTJJ$=9N^o$p3|tvA2A8X^;?X# zAr^hgzRTX-W0cEn zr~?*cN`!s9sdz%ZvD<6KuMvC9k)6ERF=gj^0hbtPk3VO9LV~c`N%RKPG`*)UKTXG+ZhhX zdE>N$qT4~C>*p7b|L)C2ruChBEoZ86Xa2_nfiZ5Yqc|Sb$+bu4Wm3_`Dw8#TeQzgwT z*Z01@wOc)ZhO`A~-Pzl}!~XOl9=pZ2`ZAh?Gdgs# zVaoDE;`YeEn#*7U;J3l}gW}`kJ(==$Ni^d37YBU`!a*n%3pn$FZybIxzDy1x;_#NK zdj-@c9|X@YU$*6z4W|ubi++uqAiYzoQQCGreV}>uubq`;rF~gIl?oeHBLed9&nn|R zYw>We$-hIc!MW?x!T()<@;E4R?V4h9stO)q-|kA2|C)W*ZlgraA!K)Ukf$$`z_&G* z!F$RCcHMGeOSr*Z`(+xN&KAl*wLd<>M!+4DJ%^D&ov?)*|B7_!vU8ElvYvlm)f|opn#LHMC7fYqr!u|BCq* zLEnma61FG;>Lz|qzZRE}Eys)a7f4_^1cIn;8X3Ox-6>V-3`Cq}KK#3SSkQUEiH@PB z_j_|pc}w^qU%S@VNWnd3HVr$g`ug+u&Bf%Rm7m?;F&05OT7iK{higEu%My7%U|UIr z9nh=d$W~@8eR=hkGvoXD#Wn@ae)an$s+*CP@9(Ch{?V@`6`I)Toi}-{X{QRU&NJr$ z257m$0OJt<%ENJ22=J0RQ8Zq9@xEyeacStj`-_gwkIpw4u6u|eI-o6G0g;^NpaUM^ z&s#q1EqwK}O;>d!gvoFKCUB7}7`##e-xNt;tfK%Y-v$&tL*p)!_H?bB?x^&BOJ@<$ zVCIbjW9yiIn&SP4z~wQ$+a+ev!a($0$Wia2_0UBa>OI5j$|05PM8%6QE)W78E|wcY zvpw89YjXv}2c9HnevY5K7t4xL6WpwwfBYlrJBh{6xLo1z8e>J` zPJfWU5_@rpvssk>Q|Jm;JY$$00RfI6`&LW?7k7e|T?p8RQBss%z8`kkgs&|cEkq1m ztTEkB+>nMSY#;$!v-mt4r6)RO^#Vpd;`jl76=ivTgw+d~Zyt#0J4YGoN5O(Ii;0XF zY&p?QNeuM8t?TRioK*~$8&cSd1o~esUSmw7&BQA0e`$-cu(j>PGEK#vJW>I3-Cawj z`}tnwRc`{!*uXC+p3Lpq(+)q;({tY+?-F zSZ1eoeHG#h{GNF!*q+w;9@FQ(aqRV}Z8ayIWM}adUh$Mux`J($^lezl?Fn1eJN9(0*c1C_mrR{DlheBO*m(*j-wQJ?v23hogh}Cw)&Iif2WGAbhSHy zk|F18w-r4pIXyL{`@?+OakE=>F&W1fD;Y%45Zxx(S#Y$sp5!KGf zwpu+f&J0J16mT){8IV2Oesp_r4C>NSrH3eeUts!Y(Ba^5^ggE$(G^yjDt~(vnyeD5 zIZBCcEl$Z8nE`Z1{q=Ax9f3Ltn7-B1BR&^6jr#J~o|{00qOy4{CP!NED}hQH zIltkVzCYW$@v{af%Y5givo^o&8O_(np_8D0d{$E)jMO! z8D60Dl5WoY{Cy{h!^u>z-r>VhOYq5j5I#3OH1b<}=n!w|YxkN`k)VGLcWugTEGB4U zp)MsSFUfHM{NwvKMz6$t9usr`vVIM&x72o1K1x0pF_5rew7?BJXQ15fv@9wvYZ48A z1c`&7Z>11q>jpjZ8beXG-xs#YH}3eGZNQERh%Ff=$?EzveC#qGf~9*Yjp5*U*Gl5D zTUU=dS+lzmlSK`ly9?LarGb)OvA-k83MF+X4fg8oI5D_~pCdboBerP1r*7e8|cSW#7uK5w#dq(=!%d*%)XY5-zg-?VoJdK#7!}+9@LpQ`JPt zSj4?H)y(Q@E`u=M#Qw}K`)EQ6p{7yM+HcPi^hB(5>@5o%oFHo9ri&^6cH?0r4Dii6 z^FqZ*p?lBFX|miOMW-kqlS@@lBIly3aZzcg;GA&|$=E)cW6XNXyz%~4fZHK}_7;bj z57_U>pz*5a|Jv`u$3RZ_4)pwI3nEdAJ|O<277g^{u*110JBb>3JA{gZ{!5j1>Sm;f zk;DZT4ovhR#$se+bN4K33nZ zfz(Zm1@rmlkSfz*VY`iK&qWQ_iT$O-wmUWDd}17}-}4fH*syZbVm~v)wz@mlj7Ym9 zul<11_R6xdx9^%%_dh1GCB~Au-x2$I^v9^Fqv;os@TMbyEF&H^z0EH9R*@-lX@WKp z(OTS&R|3ehelAxQpf_s;A&l`owoFox`T;!1R!t7fg#RD(KN3UE&d!3nzh=#GQZdie zU}gwl=SH8?BJ1hv>V%l*3Shj@Uy6W>?fIG&PGMPM91m|A@FiJC+E%raC`Q>F%0yLv zS9zqA3QqSZ&X1N6uu(Gb3J;bgl-{ZBp@x2xG&a2H;cO9Tx!v>NZU7@=qG9E(4Msoa z2K>_0p=r`#Wc>&Rf5z#;OWBk$nUI4xySQXr9a#}ei!#es;u4smV6A7-vH88zRmEAP zRE@?(;{c$z`?tn2kD5cS-9?@zn<~M$u}vuF#~Y>+<1#jP#^}{*$1_;3U8S|7QP4ZQ z%#G6NJX-qgH;8ZF=)VZ7!ZTBs{PAz2n2-v5L~7xVL|YR3L0AxI1~Ywm{0B zBh7gb5i|xst`+>wd|V_!ZEXz?(cOOh8px&Nc8hu6B)|<%3FnXxg}n96&1Ej(m6Oj+ zQf9EyADQT~EmeW6dEOYhoJ`L|e7?j=ac5zTTjcj+5|po3BTnD^bR;tXVr4@%f5ae~+6+$`Eltf0WNX9`p{6RU1qmu6a; z;Db2%801bAEzI&R&Wh*f%*rk8Ori#>$jl`Nuy-|pfoa?0>WfExyPN*X(hAZTfAW3z zQOA{uU4N93lilYu=+#Y{ z>ri}%DJ>8TqYx%n3?a_WYI8Ra)QRxNNy9HoG`eMI3lf_Zg%v$MIl|OZiIllSK|ylf z&JznG-;0@yern4`OVt)h#T&$%OAbskR#cRP*l3tluyWO$&!pJpIl@q(gfU%hpZf>| zvFDvz_WklUdc{;mAtmVMDjYYr%jj44snOj4!1*kb;vsSTNFo?iTd=Y=*gXq5iYxS+WiTMhtOxI?2VLmRT<3F&<@~k547wS^Yl;OZj}x&8GWX@|1>(IhNl(GB=Yrlz70kr04$UJ;FISF*DXPh zM6i6(V-qd~6n-W+sUq#nLG;mW-L(63EgQelTWN^XBLa=Z6-MRc{gxE+^Y9>1Z-G@p z6OGi6`War*M@BW#=253frQ`Y!UnKEFU! zz$SG%mvdwzwFDP34y^9J{0RN(JjCe78u0aBp1YQB46R-Q|A;Ul`@l?0x>YqG`Eui(wGC4C$l&q41&zJq07og<*e-7 z{ankQ6KuXKeLH7Os1y1*^kzQ!v|USt#0-vhWt+0@`pBF}9T7;B9tXwJsJbBwq$v42;Z|jNrwDTmZIa81f?KnW9CS=EhA;8 zd9XO8H1@jC+{{p8+k3H#8)@=h7T~^pz{(wy#a&@#-!720l-8^It1Ad;VHu5NYifO? z73ebP?n$y^p6*t4ZTXY2c0os)VwPabW|tSiG&Z8^XhCyDShFM6T5C|($d>x$^~>PM9W+HWi_*ZMkxbFb;aNGYgZud&t{1T)ndi+g&LL50(m;}+TtZ}#|avBYgi3e9g9bP2yeJ~o+P#Ssml&(z4Im8*7j<2@;H z6M#w(gZ7}$S-;Fd_BHRNe7Ns%LbIZykF?W&+;yk5p zIV7$h38}LVW0lJj3X;F)E(_7uP*V$zY-VK2&k%-AjFL-=(qIU=1x zJ|E`qHHT5W)D4pl6rq>-8;&;e_E=vHO~i+um|cb&2_#3VobPhg*Wfoa)UN`;v%!i> z^W*_oQ>u+eKiHu2Nk9Z~C-ds9Bo0ymrya1EAl2D?j5bS+H%%z~m_0*>7pcr0!^{W* z6=1=X=qf`K~ThT=nsikzL*feoiuuV!c+1y9Wwe$9GuqJ^$$l zSe0~@cK1T?cwV|7(NexYHO0UlKq4iQslx_#WF=Snr#?rB^BXmbDWz&&>L9!3JXJ}U zorLhz^n3w65kMfI4y6BJl*+`+qz=*wyth9=~s56;Ou_X=^ zXx_CYyTVVauhgK0nJ6dCFYF2#8C~c5nkWD-q?0dY6;1IEhX_!+QxI%_95&oML5VkTfIaGJu(@IcC;R~8Y1DR~N^TD=!nKw~s}L`nI(b^x6U;IaCwq89Ea zQY8+AYv~^Nh+FUi+W>?lL4$&A*||Sk{Iod{Mn?SoBMFRy97N@yuKNoqG$Bv!kTbp= zzjM^TLfhRzFx{)-I+ZvgO|wCU`jb=Lu<;{qxG|}jP3>z*zFMqQPD>^1%1fVU`Fq8( z^HqKx+r1COVDbBCIn8BD;&vD+82|Yq5RtH`Qp4d&U+>oHMyqK0h7E@@kb}sQFw9S< zb^#Va#u1^ADH5n`zFx^1Rqkh@rf$xcqYuloJ>nVY%(v^lS^1a73V2{psaHF5n2Clo z*fc9i(b@$PNWX*!n1XjQdN{_losc^k|Q6})r-3p=s;0j*|b{hit z;C~we?S{A|Rok7cwx!NQ7zvzt$`&8;ld=44{CclI(!i7>w2IPL0DO_bQ;j*Zuc3CW zO;Tf|(Ja)t=t#Nz6{|r4%mRMb!fjy4<%;=XKJvD?B{~o_22rm#SThv@lqCQ_`nz?L zRNkuTbm1!wX16L15Si$K$dp&|^8d=VIH4F~GJ#{V5#>2#91qcC_n$XbrdQ4h;KbY~2QQOk|bD%j4 zoNd8^p_>(v_~MZQbJzk=6D+9VMeE+lnl~1&$I+OaGOg&3Cx}Tv=}z~%nOs*tYIVdM zfO}*0%z=2tfBqtf5aqok#uda|B<%MVcdr%disIWq7x%JlN486iTk(-fD+wzhco#lI zi-oL+Syr`3lDKR2ta13McVd*HZ(tgsgq11i>-}@CSJ&|A#g=v6>08DxSbr0Jradzo zK6@Jw=_ohw2!eFGFQH?6{=bf#;G)pfXKJejxv&+laL{s8q8vYC-M*=D&VGm(!WWpM zD)tR~HuK57*T1ruh(emh;6Nr6D1OVl`g!dU%T7Z6XH>4h+USPbbwGg-n)IowO7XB$ zW1exe6zCU7%}g8^^9^D$J{pus5IUlOv9K6fSzW!DeSdO9q)bO`ZP6S=^?zl6&kcE4 z78eVd-vYv4Xlf>KJ@gdtL0-}SWaMI0QmVAAV-zo`KYc`)5g&J@rK@CSsqSF?uhz8y zl5h%9ZQXyCELXMoofQo_@(V0R9ona!R;;#q@?RM3iI8R}DP3ewfh(`*$6;xE6<@BUKY;T+h<1oO<&sv(IFr4nx zG`PFe!ETT-NA#Z>drlY93358nIKzP3pMRmn`QGpT6Ii0l8}DT7KEOG(=9pfoL~oZ& z5nt44-}&JzHCIYHT_p-hf#sdb4v3bYg}XWfM`jl=TZ=Rc@~!$}q7Qsi30=w=n|Lk} zol;97uCwZBzK7yn>?21l02NEG#q(Km0`Q0^y_V_m+o0fE7$K+4waxDo_B_ZL<}G8O zwjavh>F>0Y7T&7^pCcp5Zf$}*U@EDBFiljw_uP$l3$xw|Wp7tW*Ah{0o@ zW6ehMjdN+hg!M7dwDo2f>6TTnQ*iG*G*L^-a`LNZUNqIffCWnXm@J$$H{+M~Z;O^S z-eUg}B+wzCh@WpUiyTytqhztY)^@HZloicfOXGqJ#zY`^IFCPl)5}S~pB#;xHhmL1 z{%jdhXG~tS11a4;)%&M-l-g+TZnQ_Bp zjy43CBK^6W!~nuQDM-z&gB+IK|c zHOU+=F0s5NVo8#d4&)RY_+ z3X8FiNKbUGmFv;DBl2$oqTQIe`UNhe#e!|e|hxWuNl6hZ8Uq5-^qIZPc#Eeq@% zch|Y!rY~3gFHfn(D|;l8`&jWtdkPmJBC-XoET%Dw_QpoS;5P*IGxZoFl)0Ee!DY-0 zNj7&0A*X$r^_=IbplWZN+*Z>i>ldfz&)yNw9LEd&%ke<*oEW1l-0F< zUGT873T@Z(94JJu4Oe;~J_<=BLOtK74sJ z$-%V6^k|)&{N5);bx&Yk)SB{b3Ht1LjxGk&e-h{~-U9AL5c{EFn>frPQi)c(fO&rw z(pn+VxVIBq`)=uZJFlgZro+fUBtoU^I{b&7Zu)$_t0Rax?DVKrl=;J~>t(Y4OxJMA zv8Lp=xHRU70L|W>JuJv$f-mmDQNHI#-nLv;(Ccz{i@MFVjA5IP+<*}UTudxz8zAi* zJD>e5Rp^WR>z$W`hceN4tlhTL^(piGi)|$#g((as_x%`pdY-1mL zc_!S!OEKChMDYW(fu6$rGMQ&}UD5=6eZ&N4N6)EXi_k?s*-Hlf%>c_NhP?u?;Y%_2 zr=7j$f&ctRyDd^Q zy)6Hutl0~!6GHMSDc^g^;jZ)?V5j@FnTHEA?6u46F!R`HGP!q)7`)kOtNuX@;d;Xg z62&aLT;Q~uupprCP3g#g{|m%@$G4~-aA>#1d~)(G(~QpYo;qWz#_yVItNEa-1HL$4 zYb|Jp`2qpn^%j7jcqWa-n4vJxmxSyyz4V}ah6w~vdZSYU%TVLjhN%oRVoGCtFwoQ( z-tXBU;XeQ45Wi5M9$*}ld&V6wGf|#6_Ibx=p+Z@+LZ)k>GjR%4@D}TxA(tn2mK5u( zGDt{TY<-6DHWv*_7}mvJA59bxr1g`INQ&^|o;amOn5uo*Pa@f$auCc2iM(T9DG4XTvsfKLEmE@H<0Jo z&5A;W7E5oNdjH6}m4sFxez^XW)b;yT*kQsW#byLAlEtI;iuu4S$@=>7!so@&A3$K% z|Keapx-hbxV186+F&>7=@+`0niA{yA=~CgB55RdB3=IIiDN^}B#C3)AdhtSkj#>oj zC{NSsUnxAStbfAFb5-Af%abxk$O5*ZD+3U={zxEzfa&o;nNf*p3i$jQ{iY58rFa@( z-_z8YNi@a@Cv{v|B)$4$o74;ozku4M^S4E~+~{!A_?Z0Gl6T0Ro4|eV(b*96VRb|M zCCx*V-OHL6l4bmXCS*|D!8bU{2kV4vG}M%r-x|24znXdm26{n(EH_2#_Rmde)2Ylq z#&9)mKml-1B`CaOcxF?GAa)Dr$rF_nja`2CjInA9#!Z4aL zB*5EiazcuG0NT{ZQ1f1UMUM*&orKaRR>UsWRq5*N^FDzcX6p;$;J|Un?^h+{+Z}wZ zQkzF!zj$W7IMBBYA@Avx2W34(KM=~ozyLnR4OE8(QsFU_#-v~~so3lMqR^McZ=;wq zREQYV7*R41EZb?3b5ylH6MO|c@*i8@#})6H>~opGW0+o$jtz%LWG@;aw%=#`@@Lc3E<{fmP7wK&Oe zyK0$kggN&Ph3Q@R@hiKtwb|N65=_#w7G`C>0OOTIYhpe%N#Q7Wxbc4CwrR^oTXTp7 zUj;I#8&#{5(=&y3QfsXKt7SpC{)FF>zv>QqaOq-Jp{#o)r= zKeCPd3Y&BXUf0z-QB(%=KX}PT1n2}F@A73IQIpm@&&I~=j0(InwjQE_ZOGWq@aT-r z|GC`Hr9;%{tB89@$LU;O2M*Cn5t&kT6lU0jEHGGu3S@#Yo^cY{h;QYIT{(GYxE@ol zw{b9#-*4?|VDAg+KT(4k}yR#^lFfNie@F}DPJd0F4h`PHAjxjpqC7$=3@ zeSuib9Y$ti?4tqfMCIvXZ938gaCIQS;cruqm*4O2zti=sde;%Va=Ux7piQE|c9Uz& z0SupDpZXnu+0i0f-dih5i2hNFdELb6If|yZP(50oawy`EXMKyH-1VS#vP-9`FPfMd zP9GsdsffWIcsFS=;?boVVmP~pi7vf)T@vL8gDA)&c%Ui@x&nDI8TNYiFmXB_rSOD_ zJXZ}B=u}bVx5sabLXAZZ&yRK-U;?EQ;eM>22UcKp%vXi{)|;n_1wOTUF5ZCXb8A)F z=)!>J?od#)?!;fk%d9OVR~>x#%o2_zJI8)(;0WS$F#1*0S}y%+MgQ#w->iW&i+h5p zsHX`9C7}3ngovbf?lnVF{z=|ub@V%KQp$LMHK<1GE6uOCzr8o--eW@o1Hnmy3J6Zj z?@VwZQ4*9Ihgy!0Z$6lsbhs_{cU$Suxz^r(?abR>tu>n-HG<976}*q_Qlp<)8Kt}Y znmkFqG}7lE@IjQv*^%JYiu<1J)gywB`7965H*e+e4@q`_1VK}fw~FNQgLRerf(_k^ zz{(PUjL|?JY0s51r68_P@K#bKNJ+ec;N>0C-KzVEW*4zSV4x}FIqx>`&haELkQS0P z!s@@R)nJt){0zX`4!{2PM<7}=e#60$c0~e(;B?96cOyg3;Bb`xXy>;zozf|xS&22s zB=|Ix^Gb5mYdKjP+4i-Au$ZA|3glx3n@aVJ?xj~TUELBOk2BeIon5@3dUQWVs|nEl zRevSA&_|3}VzhJ(+YKgzqP|Y#Q7aeTb`z>a3`!hoWLGiW^Js$38jDRu3F|=miU6S` zJ69^#U@d>p)L9>aGccR}fz8O+1sB>0IKvJqn->?0OpTkgJ(EGGo{1h-9Dr>EX*3)F znW1CwY#aesZ^dWZ4?$WY#0VqXkEkujrT|Fld*Q@;`Ul>hxbL$fac3Jb&owh3- zoD@LLz9Yq%v7j*GnU!zwNY?bB;kzCl?44OMtDcHBP>Z!vNT^Q)4L-qOptMs#Af|l{ zf&#Uq@H2TM)(Pm{Ovo7<_H905{9()^g6txoKpP|j*-Z5y1V0@d7XHy5BsWSzt4kGu zzThyL{%B*WmfT)bsaXnbggN^DaGiQfZFe#Ko7-^>p`!`bEg%okDfPfC*Ykio-F+d# zb?`w;aQIw-sjC;=6?Z>VERfa^wR*BriJzgmmAAHh(~-YP+K%=#6IZ6@<22f&gq}b^ItmnXfHQX0|Np11BBj5B2jf;E@J!N&%NHT?4;gt zQQ-(c`IXI2_9aJT=Hz7!`y6jAz#^{$e2wOLGond#OG|yXSCN(jlL0=iPIcpen#*Ns(ePI7 z0=d-Fv3~TD3$k#z0>WpOtu?VlTUvYH77==Wvr2sz!X#gexmbdxz{gD+lz7kWF^%LM zz+1={`6)lmr!_4n`mdsLRlST1^hY7&_h?$ew%oxTvhJ}9#jCmqUTea*N<FK6syZ8hlVRVzt}{+ zOSCleX(X?t*;srm;xxGI_bcL|?wsO}T@g~VC?9Tda!)E_A6_n1QwX}VYBBALk^+cl z3#==i3z!ox(yCJ!E{duaE#>7* zeTD?LSS4X*)$7UaJxVieN~elLM#9DK9>b%p`}gZ)5|La5eBD+bz^zyjW}Fz=Zd^YN zR9u>hhg-Wg);YiMHH|ly;YYyOy+r@%NA%X(d^911D2O3&#wxy6fS~}OBV%brM{hSN z#YB9g;j?Vh76vP-gDxi|h&WerZ;Ihc(R0uS=)@<`B~Q^C5|HQ=>ohcud*hyIJ`1aD z@y8}gaf0N_Gnp*Uvt)DHSzOhOnZCKwL_M;vH5FQ|lRPh;)UYmTidP5Nb2B%oz1Jr) z4I^AVR2l@}Ja$&4yPWstg&h@<2z&q?ivt%(ycMp=-KD0IAtFvE#TlB7%4oLOc}J?Cw?7M;zfqGqK-fzHBk z&n~_bmGT*>#Ix811x5gcw%ulTh$~Db{lD%OPAkI{HcxhG!-x5LMi5ogq(Z-R8`_8= z3nL@PYK$>{pZ!1$l0u2x9>Lnxi(CKUMzj0ceubQAq_lb`d9(x;)5g$89vY60`7cv6 zUIKJ+4oy1SpFb`MEQxBAz5jayJtt| ziAnDLf%5=lf++z^ir<}q!f_$+zL~?>pML*wvkdKSid3~IDam>{{LJ8vmT@`XCKz6GqzJm^m z+~Lvj9Ea~B3AZw`_2hH&RI!JgcESeYZrho z$T=W~^RPt2!5VNuI9~XTF=D2@oyXGv_oUp?d6=iCJ2aFHZ?m;MSoILUhqjQk{_x(dF2~=rV!$3=yL5&6{&x=kmw^ zT0Rcw^YVWKivxkB=s3RFox+P*8orP#y^R)-3Y($p#jJzH-r^^>M|cm0k8_RbdPl_>2E69Qt)g|_g`WU>9ZDV`gBa+?Y!?H- zbvZeaLmImNP@b}uL3|L6Oc9DNRph!K|Nf6!)s(6CCb6p6BRi%j%BXBB(hS`3$6uhQ z=9Gi>`aG|^LIGu1;4lRBSq6(4mmr!Kg{TTM4PmX%DCsyAPwM_51Z}`hRaf) zv@>4k$?vu3juxODA_EpqB~PDtKW;+86f4?430~vg#t5i8ZCP+IzEg2Ly`ng{5^8$3 zzTuP!ld^>odP^VQC?V(A%;6z$*($3XslUiSeS9{TcxR@875W7wG10SC4rNoU#o7gP zCkiLJ0&g)&Hn8Jc8OcKsOZ6~u?N};m9x5Pi`ajP?I3|=Z6KO5R^U}JZO3lJ!xN*EKZPW=!yl_2ZDskLlzL<1I){Vx zosBDTpjM6pTnh$j$X^8fO!Lgd*3H6gu(MMa_r=5Q7EDnhx-YE_70<$hHYjcL9k&fN z^#6X{^6A7ZG!+(t0SpGG@ig9jZx>bk!lxMm!g-dy^oAhsQ|1zYl)s-)vqfAnq0DQu zzx-=!59U&}rNFr-3i#1PP*a-yePHU-0ehR@3{(8{DJflT6-T~E5!d8cY9-h1DP{)~ zr;)UuW>HCx5-Vi9^Woptrap@D^xc`oqT^iM9MSp0l47R`VuwRhM~{dsT5k`!pBN=6 zkTsvooTquGTM*}vEBQ2lf@n}a1;#Br0DVz{7@;t2phkeN??G67)I82>oB$~=V149* z&nhsqq zJg*mzu0Ll_!x&UzVi&s;G+8KJ1#;IqgVP*P_JlPv@Sw z*uNtYK95P|R^)p($C3V=x^XXCXppFOf=+zD#9+2h0tUuZz4@;-597cAw(A&|?gT0r ziAF_VKWn}+_MCVuxOv=oigMsRq~vmO?)+pD0AQ|U1+um_LEvGmTv}&=843SSO5RdT zmYSIIrX*v;-bD**XHx{#Ih}f#h<{PQKzC_(?kjYh{OiAuwdXgS$6?8NBs_^+Y(kD* zPxoa+yZKU9v<~2g=+AH+oeP~Fx`#A-TtmDhkSjPS2Rb2p@i~{Y*;%3g(?uWvX8>L1 zXA@jq=RLqF^DkP^GhH;;MWCDeBy@wldmXbKg*8F)Z(ip42A(%sP{1J;q5ECB%lF7N z#cvE}d%;3OtXOJkDM|YH)%SaAB4z+2fION{A|SSI31-4MP%38L_L%;cvA0=p__Lbi zp)=7{XXNAk!J~mMv&9XGUqeM+wVQd)j~hNo7nTPl{t7I-{E0{e#ZgbolbH41HX*yh z@;SmTcIdljFIp`k*0Ee;i{I^_Gr^LvQ)_qpQKd<0{@#bi$tmMPvG7rn(4N6D| z7Vs1+G9u|#;GEPBc{o(xy0;sL^9pB_=zH(#VAIJ;M9sfG5d+rmz_FLpPMab#ii6#m zbZe-PBl=@Z>g&%{!>P->(fNj=&|P1A>nJNs@Fa|p>82tUm*NU~%;3zR*k3aiRy|oG zo)d#IVG}_~aFkbpepOEfOh|ur+}KM6E|-i`9QY%M1JD7U2n&z*S*rdE`rkQ93=+7) z>l0genok{#>=4nFAbkOJGcyCE4W9U9ql!t4%=Ux*_+C|eNZGQ?`k(u+y^RP_qZ*-L zy|M5?xbCfC=V?N#FI%Woiiw0tt%Z3~;b%KF(!XYJ--3Cb{-5gNDRJfH?ow`y>qSg!j z(eH%aL=x5VupkvPjuGW4Ctn*QOgVgGSNfgvQ(WxvAp_!2j^8 zZY!F8JuDpcr4UTq%nYW|UijO1l=)bUmCYv`DHb;_!1$^kBZ5VKNEy;foar;`6gefE zOUaWKyx*+Yh_^goh}ikNuo+*AWX?HFJruO!+$#CFNPXy_5mP@Np~o(KH`r`oxs<&N z8`KN3jttSx7Im!P`TfRx-|5UyPnms0I!SBG zgxboK#Lty_4+$eT7+8eKqi9^*+@U@fB#)|IifeRhFD2ekfVh8G1$xu|2y7az74^a&R45f6e1JL&b$!ii2L?17e_hjG2mG53}-{4C# zBoh%tfT$3zV0CVEIve9KmTl1fvoDwl6$F975r7vNom{8W&2?JMdn*2Yzhd-(H_SU= zCWIgy#HfX;sA(0!cALHkOcx5^qmFt2RJD|!7>)oghLRqCaOyV4lyS&a&N`#Tq>QTz zwC1KaRMqA*_ZyZ}MF6fU@cAV!ziYCvR^2nC=oL}6cvgm~lU+;~6Zp-W+0DxmzlX-g z1e_oLYMwu9jYsK~sbz>N{rt~=v%PZ*X*wq*s;{~39rzv#w*gz&e{k!o_%&>7`+t`X zr{o3^P4i8ZKMi6sfA|xh-M?F;MXX2Ts0-R+{8vfilW}5aWhJA)JQfUGNudE{>LoFN z6GLF0db$2meeASBZA!?$o(8wMcVC3S%fM5Io1bE&?3Efxo1~vV_I!WT@EA`-@BR0! zeIrSCzv|*H(Kwa`s=jhQy34yw|16qyOB?%q?fW=2Q`%f~G{DUH=Edm8pX1Gu5~p~A0h73odB zH6zppil7RpqZ}8@k;Z2PFiMbDq_&?L(L*4*8I~0Aji|K!-sR<0sccJWf9x|(4wc(I zwh*>H4#=JPm9#y{HJHgo=^L@&=rs{9HRy`jdbHN^Ry>@QWZl?H-T@a7l!;@dPuey` z%)>*99<8C28(Xw#9#e<ZE(IXLfCP=r#~@ITpkZkn3nPQtT1&d^ZmsC(SYEj_q^Z

UU8X-bThSNfijMLZiLfdOe3{MFB(w&2`Lxcgw9M9+N+& zj!*q`UVa?*qoKqJ^)2pb+2mP+Wah!k|M>s2VXK#+#s5Azmzw z4Eb3Sy#6y;(*I0wW`6H|Nt(ugKf;kXh^4dL(owA8U&0xgW3+W_wAZE4U78qv`K~Wdv_JS#TRY%pd4+9mePr|ZE8UA1 z`+oPbMo7vNI(RbZ>a`5BXAv1Two7%y(4^NkF40;#GNDK*M|DU9kFw#x zvC_IU^2tvlfi#w@!IuB+=Xku-n~~&yS-CB`@qKgs?u|+jCx4(Lj<`ei*^d|4+F#Gv z=8f^f{^;B$ZFI^6gsxU@T%qBgvoy)AB|@CpPo!ku8)C70Bw3$B z-H@5#3n=9}e^76?dxYk#OIn+4@@_Cqt{qxMX=OH-YVh9)_MOo$8Y?S8{ht>_BPgQu zi%cV4vk13A%;`t-ikSJ@xaha&tK$v1l=)-4ot=yyiDxE^efXTkfzBmFh(=}M*VMOn zX~g?WK8;!yUwt2AKX=Z+x}JDcxW z!hKc_IHuO}*PO7#7Fn6_sn-^#!+2gOOW>{D3Y4TPa&@L3p0aiC#u9&ypvd))MN{l)O!8u~ zw9=&?!&(hG*)STBZ^JsJLtw+KNB&{3lXo3^Oct5k)r9)|P>1sEr&GE+|025xn439sGMxGqDjsFvlZng1;mj?stD=W{^sae5rin9<|e~oemvK=9Frh1uv zdHek`#_Z?Az**LKvHH@0utA*D+@`U-$Y6RqwfNlgF7q<=V0j{cdwb(F+}FqU0+r%d zJE}<2ebq+i)dw1H*!6uVi)bb5;hpe&qN1}wR|yY4#_hM3eZ1J;-s;vsP`TDy&oXj& zv`3z#34~*y-R~=p45RuWKIt*}Nnr3Me08HTwo_N zN#u-<58KPnWo|2pMZM%dUiNRwr1g}l`rt3;P0zku=~1D(#xWkSa^!3sK8X*U-v-9F z)$W*e;81Rhj6@7e;gX%`^gs(f!II-V8=x$|Cc~-cY_!@1?4H0f1UAbCWMKJSq zew+G#?Y-q&RP7fwEC_-iASE4=($dl>2n^jFQqmyZB_Pr;bhmWF(4}-rcL)rfL-)If z`#Ij{Pk6rk{NQo$Wv;!~weno&T6>)OdMFH}+txV5{xv&y>UVdA*O5EmE7RP)Gd=>> z&_e${cSp3*;f$-Sj2MKckcirw&LVyLP1U(nBum!w&bs9KhEMPHPvjSGma6tgu(7V1 z-hy6;xSkAPX$^SL^iOHA)FYd?8J}iN*sn%v)qHjLJ%%kV6VzfNAc65dEU-an!oG0B z_0|#5*T-S%`d`*f-Q5*&W}|iy!vZ3ts$jUd=*9}NF6DZ!(tbYe zx>gT4`_xvOi53?K2ENxD09!Vo5@~wFKo9xWd46voXDc@S33vw%dd0cgy27qFxde8P zUoxX>#C$vHAHKe%!Tnf!{WH`WJmv{A^5C=i9uSs5F=;a~!@GH*M(4OW^fIDl6~=2S z1vcz&!PKOe1Tr)m(yc$voW+|^b99S0h^QNdKpsfCRKPK!dY)QzFf9RBL>iRz!~LsJc~x zqUvS0m8{-B*INer7B*FXOp&m}zTcf@lgDNK@LR2(QD!A`&?e8u>`nCP$5SfE^|7a! z>b~%)wjewfx~WjM`($}IQoP1TL_Jen4GCh}V;Q_j_KL>XHpI5x1X$nuSkqIg_X8-| z7tCG1esyd(mOU(|+ye}Z z1F<)@8^K17Q$iuuh7lU*V#u+OVN2G`{fl3Ju|T%KyQ$!Gjhzg0cDiFN)s&+(*rBdd zPC-a*nMo6(=0TANwIs2aDMI9s_$(eNcNh&iA&)aVT}%0{g71cefON+SU`a=w(O1}g zj{dzA27(_nb+PyZm0SoAs_uF|z$-LN}gnFz*g#}Rq`k3)T~ z)88kkcze8!1G5@Ba45{4%*>G79aesH|APrx1r@m5_>P8O=l?n{_+sPmqxHL+w23p7 ztFOdcuCn{ax~f8BRlxd<5@ik#Y)Itk6PiYoK#cGk_#8h9G(~ZT^sH2u45f~ADKyo%HQTB~17T66Ygu&2(-E+aa&by2~V-e(~lKKL#G7fjTm-wX*=G+L#t8I`)e%jpM@Tn$FfJ_Qha1Cz(vJm zeORxqi12va$vC|=K7CX65Rn#ce(Wjm^YIm;#DQ!0{mIRan(v1{#Dd{~{$I%hCDxG( z5dv`791>2AR#d|(timeSF7dhJWix9=nL~!7nkcwe&LMflx%|zp|Lh>>37D5ea)^l$2qKs9$sV@H;4PIfs-|gG;Cc4x5?ql?CmzXHs z;-8lKKZX^wq((ZN`^2WE5|C+^D7L0|W8!BK5Z13$lcZ&u%qNLe2Vjk?| zd?3JM&q%?pPIN8rO)rla8I~5N_iM#(HkF&lrxHZnugtMb$oj_rg~mMeX}6X}Xfucv zmj2YSM2*ATCnS8Nb!8r zNzU0RV)bV=N}{*>m07Ir5?hJIj(3Zaewgtc&U^a|J<&+5g*u>oPS?NwQ&Z7j1J@!E z7`x{MBWZBhGNzDGCR00#N#PIp=;=FfR(r7Gd%#YSYs14L>g%|RYb+vQF?yhIs z?e#97C(EDDEnrB}k2RNO4zX<{izT#jNWsvI)9|$gnAU7qtP;FToXkdAW@T{Y_+w$q;RSrI!I$Nncnpqz z!%-%$#OUZw9}fA6v+aihoF|wZiVMaz1Xgq{j}Fqn{d(Wz+oMw)EQ*MI4MRL;uDgph zK%+m77aiaKnr@l?HQlycp3pj3j49*57b^n~=`DX#?F@Eo@Koko-U$(B#>lK@j?vu= zec!unrxP{_=D4QHE^on;lC>sK&OVVqrW=S#32|7n2YanxT~hs+uqe4Ob7jIcb!o9Z z%Jk!zJ_a}88<3uu)YqSHzldVf73MHU=9O`~Bfs1h-sNY;O*Hnapje*qvJ(>%`-&Cb zgc->VPx>{Guc{s5V}HLE?I=O?)o(B|mqH;2>yy{%N5nKNV}IMf>bfC{&Gg>F_FYN! z7}YTdv$1KHfrVH+F3X)!Ww2)_rl={Evy!OLxZ}B&gv&%VLcyXL&BdQtbX>(fn9aVf z;6?70d7glDK;D4u$gg(_`wU*9!mLw*^RRgio-hKFb{;^9M%Y_+mFylSYXeeXL~ z{75gt)y_mFlvK*BBaj{D0rm6J0WxA#Ef#tYTlq%Uy}YZD3w%b)0`AV3Z8fj^v$kD| zf^#L)ZlOKH#qM%G=uY~r@$T65?WBQvZK0;%aI;L05Nq-WMXl~^m9^tP&vSsqt4(>X z)iu-hXO8nbUbg>4u;vefXG5_4!vV|O$c^Epr z#Im{47>lItJBIc!RLpma4f`36Y<>7a*XSA#snw;ABk>m-Ac2jw59a~YxBF~dT&m6+ zpi~Pw09ooVX{+YYaSY292d{ZnT*}Eyi8rd%hMH^4a6gKv|)i&A<_FXK=(42GVab9%$4Mv{~ zqkpBUl`1+KA(5u|gQnZ1FPdN!WTXY|A8|ZssB!7XxQC=yqPb%Cx%;0uP6ytc5j%#w z+;)|*yLXid!0lffyia*2>>k{G*)H^PxnJSfH45pwnDnF7oQ9-Vu_TG7b?#G+ps3oS z$NG9;B(c6%u!USc$1xyW;~}PrC?36qoay8(V6C?3e@|y^lm>t+ZAaa13{&^fj+{A) z4RFcSML!~#pImba7s_q>Woc-c?`FKm;A-Q}*jC^z(Ueovk|*x{(9~&JDC@Ho1nrhP z*nKcKP`2Cuna7g$_gGoY?c-5x{E`3n%K_TMQ4nn3-Daq%fy}^+r_|FMWQ-|CzJp-$ zsV}mlHW=#y6E8(39=}1h{8`iQ@l8Dk&m!^l2rTwQE!iP;8z$4Vb4ojkZFDY?&lm+Eji-E?&^O>croKhti7+ZtilXdCUZ zqIx7pl}Lzt-R{#aDFitdo!3|G#(hyJ>i%(l;POkS5>XdaEq9n7RNG2ZQREzB?zA*c zg0g@1r8F?mPx_3Gl}W_4bcp*~(U>+)_ogxt#Tf@5!&-m;{&?LW|1^c-iQd5uqp;mz z-N2t_4X@jl&cDZUvUL|Iz`i;t9q$7x)2o_yG#ypQ5oKDmv0JlI<3ueaqlrwD0U{_Jwq zQQ36)h@rNH!F0woI!+K(*z5}tBeQUA?@gCY%L}E)01K-6Q1tZOnzj#hzI$nUTK&rR zq*zz}wwQfPgGgp>!Y(2Wjg>tlz0K{8aB!BOKO`cIIiF3QCJdVHp3TKY?}AiNxP|I!Rm6UU0JitR-QFA z4xPNuBrL~?UB5P*t7gi1xbOU0xAkT5{2O}Dh5A3kAy0R0O=C=H-^&@As=H#rM@y=z z{STXUpDVoWYAmgtL{fo8%Wm%zkyvl9%fUWDK?K^sH|DpjY1m8Iz{|(r_v%~yD-UVi z91#LiVEJP2b6aR_F#t6H~rkVL#mw|?a@@B-q<+9OP zXla>gVOXbjx7UGoxVIHYLAdv$-MZKEZ7mrB(gkQ$ewO!x_+ovJ+*bk z?fW-oTD-dGz*}?*VFoex<^{vvxChyQ17Rc~It$yp5ml+i5L^9=&SjL-H}o3B%fQ0( zfec}qFFV)?FT<;uK{zDb5^Y-}vDtID^#Km~MRV4{G4?A9>iep6()5qDM<~gHY#-hW zT57E)ZPw1j_n^VM0FB7Msop@EY6C|P^3fzN9g4U@L2@0W(d4Dg`Qdut+Bjd! zMD?%rxusnPtP3BSndzIX438^r38|?0c1|2!@Dk4$$nlh?zvS+Ba=cyo0$RobALVv( zl%IdGkMEtT>aAszEmxhEPV}?KX^nJcAcDNpQ&T+bNBlVW5(DFv{!RYrWyW1x=0irk z+mwX6LFQILk~c+(k{xkxW23DE6mg|K2>75h&<=Wo`m50^6b`<5u_+oDG=3(wKfn82 zBFrdM-^O(5dE2H$ZtZ6}#EA7{Dm}W^``zyRH~j1@^_8ou$}|uuJ>@8gcA@R#mgD3M z#oQR#OiejSY}MyK)Poy{2qVFn_>9yFyKNk29}SA6>68W9L~8k`*>p>?667n?V^Xqr z!yn`Z--3L|ZTO1RKn8_6?WIBe`*(AQB*Tup5&^?bN?bLBr9llHL-Xr{y?RrMC_{b_w z*rNn$U&ZHQP?Y2P$+LOlc%in}R-C!&_d--_4eMp~+t(`-z!Lb0WBXnQel#D-DgDHq zV!g7_LVTDoo%=rH?hblvMi0cx(~E7o?UJd+Y*gMW@u{7L>hx9=)__i#ApuA*5`A)7 z_0DOzrC_W0`?2rf==mj?Z<>wqeXPn7q>%a zn$n7Q8de5&Dp3_qTh)hM4LKo!a^~Nvbk5>pzasQI4oDUrQrCwd?TmfKDfHFBagF+w zM!V;AW_UeX9XTvQ1jY_TgW9m??o@7Q$OWG{*(O${ESSh$o8f@`k`@)5Zh^g0b|LJ_ z)(ji7W#hh&N#WgZM>B0e;T+`AngQU&gb6;0LtrwX#>C!P5hCnj@Ix=Y7cK8S(X!Ma z`dFOQ(JGF`L{-*vSgkeo-NH|7Wy>5n*ijeM&X?TtrmLXg2-kmGooFeDb{%n3YQI(4 zVvS{T%9DS+idHXsY*ZTER@%c`eLu#JCeomG{UoY&YnQ>wL-iR6JdV3F9@no=3fhPa z!zJiJ^WJW3;6=aBT>%aLi;Kc%Jp5X#rbI_q~rg zuQXC}WhA?lX1vcaW_m<0&sY_^*HJbK-wXpFpa|-08T(WlKf5Km3=a~bSeQub9aAoj zP_%a=fWjE%KoCp3iCWmc^Q1e}_0DMQMc$H>l;G0iX+1SDn%;K2;#}%5QiF%#22njZ zQBo3;x^Rila@NJ%|_mq%;1V2kvHUmEFq9^1Zqiw5CCCO)Z zNO%sS%+mP#zPhV@F>I*QvCdy^MYK=P{B6;@T%@*K6ZT&^@n;U`LyKni#W7pmoIV6i zhUEmtB8T5tEk^3;8>rY*gsjKf!<){pr2yQ*-a)=J2#x|!eH-Rh!J3{{^^uj3zeVY% zX!jUE6O69)yZhq7w-YbaU_?oNouW&1G%zJdkv6A+L4kMig=q<+=w_*PGA|6u=$n`@ zYx{%6DFkfvS~M#a5k}_Xbd_dn+q27x)(7fB@8K?IbFS(Of5UAxUHbEtP8EA@{HBMg zL|tFi+%Nz$7q4&{@BYxWV?BTuLE{Vn-zU8(4yf(j-zxGNkB=v`4r}y9^;Yy9^-Ae; z%|j)$dtlD6S&MqJ#*fO{CPgIWhg%X#ZSU3%R<@QEaYO8*;Bxo3M*YB|L^m+_;x5E_ zUg8oWE#kT+=F`k(mgViuyg_TnNB5{_Cg@T%qyaMy31dQPt#$kffa6}k`Ll`55m`Wo z)Cv&;17oZyCA8Vt-m&P+L35+-s)anN%BbzY=Cs_C7qb$p_omtKPGQPh4HPp}8c#nM zL>;OcB-0v|PR$M#$2rZbf;-1#{GUgAL)Jl)E*}1oZhv+%k9%{+fwkHY}e z=*e@MsHkR#FyQU6-?QuRl~oO?O0byWzsIKkaJ@IIGTHaM(UTEsCwR}IqmJ|Ienm<7)lXd4;$+1m>)QcqzJ(fn z-x1p=y={r`b9|^R-ufWN*TzW~ogOk%cn5-m;S0r@BYo_$-c&x>X=nNL$?j=-50(33 zM0#w)?@{}-sJ=kAiSlHv{;sK|N@KW*W;FwS@n)u;8+d)ri@a;5&N^59uX~Uz*EW%+ z+Rk&1X)bccmSsY^m6ugZ6 z^(ES@%a)ZD-D&FSP5J9u652fVZR_)u!FAe>Wh^|20C(R5?;66}DR0KBME66j^mo|YCrl-;` z+=^6J7iy~JlgKQPVOIYn>Ii!mtCj28t<>e94(&Vv4RFpyI~s8Hdl}U5zIdJJQuqLJ z@MWuWvcnKTypm0ut!!wg%&74S9k9GpH_hlY%JxuwZ8Ac$TCFD#eF>B$vqq^Sm!%IR zo16%^u5q&C31(#%ZjNNRC2h-so$E>&?1H&BlWA+{dfm&7F{ z*I5tfH5jHDV4nE3fE0E)QuCSMS)l&Oeyb&r*G<-gV_YaaN=MwzO{6zqNJRX!>a)C&uj4CuwxYm-+rZ1>lX&d`Zdx{(yED#n5Z>2c^! zpp^xV@7P1E`K2LvJ>5gV8Z&rm8=uh^+)7@da{~Ik*xtY1pqEtqr|;uG)v&(ggC(iF z)OSJ%j+@9I#auooj31C^|O;Z(=Hmr!T3#0;*$^#!Z?&mqSJE%byWi8wG3g5uYEG$S&8_SsVrgdFY^XdC`zFd z3Iz9WdZOUC@qjMVj@zuzxRL(-y9zTUJ%mt;Tz1s&}7KI#TjvnHuZLv0C*f2t%IIQIF)=kNi^Z$0f`of6JX9YYD{sAGQx8MW_6tE) zR0}d!guh>X>f0H5^klm71XKD}jMkorbYB4>k68cV6vBR=0C6~1izl4Xq@!)fxAmCf z6sj^Lfd@1HeYiel2ys8r4}jq|N9h`Cw|k(|-&VoA*DSpgN{+t~6R{x)W@``QM^g(U z(Mz4D4j=Wr%b#7|0SB?&R#RxKz5y}=>JGCAUe|cYoq%oS7&7Bbb*}`sK;-qOHAa5B zwl6=QNP1aJ2$=3oPj#+nM=oOBM2Y&Ox`rz8x-LC+ck9mB`{q|NbVH7&`>U)>4(>s9 zu7V!oIF}4j!17Gc%=&tBPwR$#`8`aSwTlJ7`azVgw?92VjVM*-Q*!}jg4H1mXHt}` zfri?q4Ry^fEmIkUGf7=l=s9@)fFS>W9wb}~Kw0I#s*6llbO`u*u3Lt*z5nJLacYF; zd+{@Q z_5LIdH=!ux^2V>boq*AfcBgNDR_?R&)K#S8tyOiWD{-u0-T9Z2)b&0;Xyb%kms=-%1f(AA{OOvkXdWH_(MJL}1H zb34;Swn99AqQDbrEx(Lj23%#h7Ox8VTYZ(43-@1q@7f8Iwn1*E7Rf7aA%Ir>G`TqV zs2@>Q(%>}9Pq_z-kt|m;od;TI*x&rS2EckoVg+|pi+pqt`K_TZE;V8!;)B#OpC(i+?BP_NW}c^z=~85P2@zm zJThG77XUHIY&0VU?z_WZPL3p<_5Qg{VdIRvE+k#%H7i}CVH^kcB^q%nlvAziwXI5g zvC_A5%q28PJXzdhrHzsiYjdG=1HycisF9a*NfNGl#=P;{K`qajpS*(jD!kv>2lj-b zi*T=a4nMLG~+vut8qohQ+a#=bH4L%sTC+It_ z&XhSL-ucLWXlFF^`VxIuHbnm8w<;3uGWX&1t|F2ulag2UINRzk``4`x#CAVZQXn(S zYr0$34^GjuWS|wMcDh{#Hi2F-pT`!iry1y|oa6%pJWSUbi&A(8m2%Y>0o*IR>>ddJ z>rDL1bg5PhkfJ@tY;#kIX)Us75JN8VNM|51hD<3b>UfRn`Y+ITy^ObX@&7Uy6gS?) zt4}TOn7nteQ>*iF44!vPqo#0kwZEgbpu!wA{N!D|fH*cAED!-W_GbvZNI0z$ChGeY zwVw~z$8oPkOxK#MhZlc&p1Y1X=gK9s8XrW_ca?&VJ5~1%!inoPuI~=II9=lf$hvWa zo|%&Fs=A{5mxH1sc@WUFvNHWL=mr+&8uuT}Q# z8LWRk3CI({$MD*RVEh^2iYdAMt*q#eVlw(N*|E(^&sg16!F^iWh$Mn+b?PQ|R(d9_ z`w|DXw2DhVX=6>hY;rTS*X7p){|cn_|1ClXt{RZd^ZvBXOK1^xs=i09|=I(e@Ba`p?2 z;y8VB$}$6g*l9?LUfq53sowLj5z-^PODAD3i+Q=e47h)wu4FWR;AGkTmUK2ub&_s#$gc1I6EeH>PiH0Ev<+~ZF@o03&u_X}Y zHRDGh$~^EW@7E5P%dM3!HsIfZECKKt>TTK@oI6c!i*34$w*hxDo;Y*n&KC0|3BS-> z;$23RIwyOD;~$leT#on~d4@4zuTk*+`UTE84O{Ze$RL*Pm&jIbx6bh&N6Z z;h#szl!lv^EbK%*$o8HEb1yACF9iyBTU4amTZa)1-ju^44k!Cn`X^KBt5W=-ke8}q zD!YzVdbhVYNNayrVEbcm7mx~2?9+5qlnTzzap42cvmMe=nyfZD_-dgh!dL^zHM>8W#$R7BmFn1>?+$PT#eYW6}Y?EvkU@ zDInCdnrNYc=Jh+QG9_X8@A9=_tkK5VTv4s!dwxG8r`x{Sx2Q6u~I@(^q*~j(iFUxAbowc39?q7-&9d4%H-8x+& zS>gLoskuWL%w^m9@D2!IO>D0PCBeNM7yL3VNG5%u6<-U!x?093jx;YZ>^S91jn67Q zw!kXRxP;R&qu{UvsuRoWeGmL;cnSxEX;ptMZZ+R{NvlmZT_w}f4n5ePg2Tx=u&?;d z0Ufy45xnwS$7;9wc*)Xk%WmnX<<>(|)8kC@q=v9ySHzm2nuO|)l7>C{1vTbFX~~0J z8*~hY6IGIzJ+uhM^Wozx+Nmy$HX1#(GA`v}{VUqGrr!&U>!rzOq%%0lIGpoas+o1B zBV_O(Ed$o>iwP>|5F4!%zeNQ>I{G$it;htF>-r=4y72LEHfE4D` z!frwx?sqT{Lo)i5t?$zNg;&mpy}iIJzRv?xnD;K5et`1$hMl#atfYj;rvO*YEF%JXi!EU#M3xL(5C z?%aw{pcVZY_Tf}O@)A=d?pk}PoZbG_y2;6DQ#o}|$Iy7d?#8J@cSTEDuQKSY@KN z9BIY`RXqf-V!OuPU*D0@bb_KR5@gY8g_5+=sCm*dA+L|97Wzd4o|pzw!dvyvu|S7y_&<}7fDj_>CII6O|rtQo%^LS}BW z&~~x;mO~aPtN=MB1#u#0Vsy-Z^{<~PO>${4sM@zsnkFHh{Ozr4t&@|WMniHgjv^AMib=30Y@HLg9jBgyMC zF`kl+an_DXd<*(th;W4$K?Xpz>*CtG9`{pqui?NlHtDrBiE9BT9t@%dr(c3cTN_m` z&(KBQ^{=yKlmQ>tE6*QR&%F1kx%pR?JGt6s2HlgdBGS7Iia6LEd9-UT30W6^4m7~1 z>=y%s80ek&X&LSktedW9+r@Kc=a}8^hhbft@iXxh+aIf}*SP(EyzmTB2A_%C*q!hE zPK7hk)D(FJsz2q@1_){k2he6)r!&#Nk^mOwC5@EXJIV*I!i+l~J`e2T|GKOiEH7Y^ zCqOn{2*2(En1B<;Jsg}HtAtu`=3t2`2!4(@K`uNipjtQ@ds5UpKq*epXJt{!wTDPla)ao8%B}(> zy0Cv@-ubK$Wk3zq9WnirAzCY@A z=cs69(L>DIac`7XWNY`*y241t`xf`l6m$y!f+V!H9$W6BZ>HH?o0iuDJmZt{)q?{31EsHej*Mr_l7zW*x7>&+BZAu5AVXlwaOr@o144 zQdD#AK&&##TKo!;v9STv8v&zJqrxI+&ZP?lYn}r4giUNlkbzIZ8eUs>;-hW`nW&z3 zC*1)7-Q6L$9(t{28+fJH`Rpfl(=)Q}O9TQTlu!EXAdywVR+MJ(4&&+Fj}t^yCPH)c zpO;1r5R7d>c_+5l$3PV+Y%^1`O_x_IKCS66D6c^jFs#sVaP^!6`Cq}qk*M?inU5{O zfwnu4nzYT->fGD!yqy^ktjb#Lpi*-xa$WE>Dz#lo%=;MDqA@)<`)AM8-2Z%lhpiWJ z>|BQU#i2t9=D^1e4F9e`pLte7g34MN@G$MTj6+(BEpENo;=2_#(+_0!QxNIp4A#ig z!$e4dko@)QS5eHZCp&DIkEZi`(vHXgk+lu9Od=xS$o)&LdR-)>d;O8!b2Dy}v!a*t z=_XP06hwW3|La6jMhp4VB~KQWuJpYaRIZo71G+DHW_!i-azpy!hm(RQ4=lOQhhrk> zEDLx%Z-{;;d$57;!EeT2bL3%J|ZfGlYd#l{GbfA=r_}N0W#i> zeC{~00W}&lI~U*6RNX<~9=2ZNlXDr{?L@-n1Z0F2G}&utws6o}voxM*S_yib!5cL9 zbOTo7)`V+_k{%Md_a4Bxx7;ye$v7+*{i1l10yUs;Hg&B(UAs9YsJJO>A$U01nBCAc zFK`*UT)=X@+rB@lkRMH+jb(z`!R-|wRZs#T->dge3|`7;cYlDPHK{$&BxISE3WvBe zu2C1u?01ERSAN>q+=H9*+f=kGzIu-BrNPj{wnMv=)2_(s#N`|cC9na88AN;*x z9*+x}s<0II&puhc^`-`=Yyj4B#o9MLk_}+pfHP{xrF6e@CB1{gL6ob={^E8f*JE)# zcqW_Le9-dYitbA%nx5x!3mmpiF*h@pn2NZpLte^LF5w=#bAK#H9uL);FA8`+;*jc= zhW4Dxr5f|2Cy;_^P={(9nlH>N)*3u~I#E3B68Q52hya)~?VaNJsorz+KS3HuwH}FS zU)&R0Wa#<=jf~}Wd)Y3dFbz(IY?FV3>pcc;hpJ__7s06s%RF}k42e*G#7$Oh_pYE#D3_D??l zNclk3N>2;g7c3z=w;oC|OZ3VbeG?Td=Z5O0omE|wZx>@s*Y{eIL)YIqKX0b|Oa==& zn}IoXJ?^7$d-Jwo^>|!_x!JL+&gUn0GNEZ-sHCajai#s*N>L{J^_&UBknBGdt9~23 zY>+T#j_nKwv4NXl_b;~NH8`-g$Skm?r(S7(?t!AVl;^-*lA{~JU(mrF(M3DUX1lBC zs8L@SWQAD*8F@8~M0>rq#)MKNYSC8*Y0!+;RkzMav^5$X=+cC(i(Kq~pYb_vva}w0 z9T~=w{SL{CPI02vu8;=-M2AvdTid9-9IP=wIMCWU8$L3FRWu7xXZx`kmh}A|t)8{{ zaxn(SdgN^2{{9a7yrL|Uk;?DJc2M@y|PKryK>vG14cQ>RFQ*hcV|lYGH7yXw0dhmTKw+EKBxw%$7tx9W$~ z-oDo&WTOXaF6e(|T`twW#v@Vt|NA#4V@Fh1)4Wg(%qcvnNFHnS`ST*+JM%C9`}<1l z%fQlbdzhWo@GfmVKrs1(@?+{R!do?UJjL#y=`r6(8Xg>>kOioLOllbfH0~DsO7bn1 zne)r29e`hRJ|O*S{H#HC^?dEb#D2(Lo#Rei-32+G>aVdsL%ZN4J?US34j+g7F|e$< zWzLyA>z=(ogSELyL*_*thrhm#V30D*N=5H=<@2os1^tV;&XUs-Xf1#p!yV5NoUAs| zMv3!eslcc@K)Yiy5}0Q?%_?HxW#?*9#n+GSWcnLnAwv@iU747-PaqduJQ6MccDQzJt%d1f#Zo1&7qF%?cemulQ9wc8Y-0jIAIjF?CJfi%=FQAn-C$Lg4D zNlprA>YqlWp7PHCVBm-=OPS_B;hEu?Ti4PpPWS zVIZuHR>m>hWaukIguy_`#D|56dW=-ZAKY$)|49LfgC@Giz=X&W0r&>ZlWp)K>|FCe z^O+37k9G*R>i=?L+kN|11s{_ePiPKi7|(S}Y4Xp1R?rDi&&J-v zJWdBOhfjw&ix^1*BaFHPNf#w#_hRbybyZGvwRI9W1LeAWYffEix9GQV7F*wg+gpF2 zAx6H^I_u1@$MD{_i?WB~#_%vy%?OnAC3mV%Kw|U}qROGggSVH?!fl?U^|CKLJ-Fvz zj8JCpz&l5AeTDHFO}6UzR&$V8CIQsWYWM~9YIVn0MnAtU%O4#e1)A)eD_0UK z`yDc0EQZrJ5~HaAZ^t>=zb7VChGm%6W9UV5M&!WJD?scUexl2dio^ciQn*h~;=RU#!tt+ z?nCguyNgMAE)Yrg-}5ANOdjnQ*16U_cJkq{43s6Lw{ojnNa5?vYXHRcnu@EDnmtp( zP2?sZ8xN59vU~ z9xW0*SDw?kKYEmIU7MjU*R5w1>VMB6x@rPIxb$Jiz-R^hL9}oPMYcrU$1W1`PnO6M zzcK`dtCJ9G=b()omDQdJ3J+FG;=D&UQH`Q!p@&VXP!LwGGw;Fh;69$g|Fo^W>dToQ zf=ZkzFvdd@8{hUx_+;cN+l(TlI5P2qX~NL6m~01Cf&l4Y_3v79f{)>>_s+Xaj;C}J z=(3XebCNeSs0jXtIsx#IEAp?!883iac8ZA`g3{DnMln5OD1#q$?Rf;y@6MD?>+o^gag6GO|tNKOC+FJ+AgEZnB;&{tQz#7A#uwH6s_ZLL&AWwVgBv+JD5}#*vAFxrfWBC}2Ek_YWD})=51hgkx*Ry$mA32jKU;N^6jivNp4LeZ7}Gfji1A;3 zxi={V46%LsBhB;U249$tZ0n)r_y)#Zoe;%AUH}P^g#U*1OI4n_GZv-dk&u+jZr9pY zdPrH_thk_Hk^YBOq+9$_r-6V>ZTrDWf@-Kl>whOvMmGTwViJSli8BtgbI^629}|cR z)K=(08z&jbnrtS?fBkZJOCN$nW}uzHiHm>jbb1U6UjvWbXYX$j5fl;5EyLE;NnJ-0Xco=B?x4rSTWeY5?9A_6dMi_4mILhrnY&bjj2F zIX(s99YX;(jD5l~%9(%NUlyVk{2Ze8#z!v^*~j?<;lpy%!i##-YM))Wz+ie`V9y2U zG$oDd=gY>3Mq=Dn!sV+O+v%VJt5R7swX<<}i_QBGAQpT3{`L9qSO+=a*zyCV`TzD( zv?E4DsH^>xG}9p)k(1{V27&tnYIIuoJlyK?Nu)b`a{Qs8}$ z6FRy)4Gsu)nQsEaV+3`6)DiC0cIRtU+aK{}ChXjW29Py#B8nfz+U z@EYSkH-p;1u)6FYn5v`%%mF_+zy_-K*N42lbaXn^YfZnq)^g>BUM2J=coa1-yobCb z?yZVDbx})L9N3WH&syg4RiIn^z@rON`aU!ffi;}b$Vr0ycdd;10Oq;_gbRint&+zSf{8gvRd=vp~lBn zy*2`UM??>$E=-{+h`p5O&GQ0)UJt*k|NZwr8T?NV{$~dNa|QoTJRv0;(t~e8HCg7R T$C$%2;2-F-ym(^`Vb!C diff --git a/docs/sphinx/make.bat b/docs/sphinx/make.bat index 02112aa5..cebc70ff 100644 --- a/docs/sphinx/make.bat +++ b/docs/sphinx/make.bat @@ -9,7 +9,7 @@ if "%SPHINXBUILD%" == "" ( ) set SOURCEDIR=. set BUILDDIR=_build -set SPHINXPROJ=seq +set SPHINXPROJ=codon if "%1" == "" goto help diff --git a/docs/sphinx/parallel.rst b/docs/sphinx/parallel.rst index a9ae4720..63dbcd52 100644 --- a/docs/sphinx/parallel.rst +++ b/docs/sphinx/parallel.rst @@ -1,9 +1,11 @@ +.. _parallelism: + Parallelism and Multithreading ============================== -Seq supports parallelism and multithreading via OpenMP out of the box. Here's an example: +Codon supports parallelism and multithreading via OpenMP out of the box. Here's an example: -.. code-block:: seq +.. code-block:: python @par for i in range(10): @@ -14,7 +16,7 @@ By default, parallel loops will use all available threads, or use the number of specified by the ``OMP_NUM_THREADS`` environment variable. A specific thread number can be given directly on the ``@par`` line as well: -.. code-block:: seq +.. code-block:: python @par(num_threads=5) for i in range(10): @@ -31,7 +33,7 @@ be given directly on the ``@par`` line as well: Other OpenMP parameters like ``private``, ``shared`` or ``reduction``, are inferred automatically by the compiler. For example, the following loop -.. code-block:: seq +.. code-block:: python total = 0 @par @@ -43,7 +45,7 @@ will automatically generate a reduction for variable ``a``. Here is an example that finds the sum of prime numbers up to a user-defined limit, using a parallel loop on 16 threads with a dynamic schedule and chunk size of 100: -.. code-block:: seq +.. code-block:: python from sys import argv @@ -71,7 +73,7 @@ the factors of an integer takes more time for larger integers, we use a dynamic ``@par`` also supports C/C++ OpenMP pragma strings. For example, the ``@par`` line in the above example can also be written as: -.. code-block:: seq +.. code-block:: python # same as: @par(schedule='dynamic', chunk_size=100, num_threads=16) @par('schedule(dynamic, 100) num_threads(16)') @@ -84,13 +86,13 @@ applies to *imperative* for-loops of the form ``for i in range(a, b, c)`` (where For general parallel for-loops of the form ``for i in some_generator()``, a task-based approach is used instead, where each loop iteration is executed as an independent task. -The Seq compiler also converts iterations over lists (``for a in some_list``) to imperative +The Codon compiler also converts iterations over lists (``for a in some_list``) to imperative for-loops, meaning these loops can be executed using OpenMP's loop parallelism. Custom reductions ----------------- -Seq can automatically generate efficient reductions for ``int`` and ``float`` values. For other +Codon can automatically generate efficient reductions for ``int`` and ``float`` values. For other data types, user-defined reductions can be specified. A class that supports reductions must include: @@ -99,7 +101,7 @@ include: Here is an example for reducing a new ``Vector`` type: -.. code-block:: seq +.. code-block:: python @tuple class Vector: @@ -121,9 +123,9 @@ Here is an example for reducing a new ``Vector`` type: OpenMP constructs ----------------- -All of OpenMP's API functions are accessible directly in Seq. For example: +All of OpenMP's API functions are accessible directly in Codon. For example: -.. code-block:: seq +.. code-block:: python import openmp as omp print(omp.get_num_threads()) @@ -132,7 +134,7 @@ All of OpenMP's API functions are accessible directly in Seq. For example: OpenMP's *critical*, *master*, *single* and *ordered* constructs can be applied via the corresponding decorators: -.. code-block:: seq +.. code-block:: python import openmp as omp @@ -161,7 +163,7 @@ corresponding decorators: For finer-grained locking, consider using the locks from the ``threading`` module: -.. code-block:: seq +.. code-block:: python from threading import Lock lock = Lock() # or RLock for re-entrant lock diff --git a/docs/sphinx/python.rst b/docs/sphinx/python.rst index 191d31b0..0ee18c2e 100644 --- a/docs/sphinx/python.rst +++ b/docs/sphinx/python.rst @@ -1,17 +1,17 @@ -Calling Python from Seq -======================= +Calling Python from Codon +========================= -Calling Python from Seq is possible in two ways: +Calling Python from Codon is possible in two ways: - ``from python import`` allows importing and calling Python functions from existing Python modules. -- ``@python`` allows writing Python code directly in Seq. +- ``@python`` allows writing Python code directly in Codon. -In order to use these features, the ``SEQ_PYTHON`` environment variable must be set to the appropriate +In order to use these features, the ``CODON_PYTHON`` environment variable must be set to the appropriate Python shared library: .. code-block:: bash - export SEQ_PYTHON=/path/to/libpython.X.Y.so + export CODON_PYTHON=/path/to/libpython.X.Y.so For example, with a ``brew``-installed Python 3.9 on macOS, this might be @@ -21,8 +21,8 @@ For example, with a ``brew``-installed Python 3.9 on macOS, this might be Note that only Python versions 3.6 and later are supported. -``from python import`` ----------------------- +from python import +------------------ Let's say we have a Python function defined in *mymodule.py*: @@ -31,22 +31,22 @@ Let's say we have a Python function defined in *mymodule.py*: def multiply(a, b): return a * b -We can call this function in Seq using ``from python import`` and indicating the appropriate +We can call this function in Codon using ``from python import`` and indicating the appropriate call and return types: -.. code-block:: seq +.. code-block:: python from python import mymodule.multiply(int, int) -> int print(multiply(3, 4)) # 12 (Be sure the ``PYTHONPATH`` environment variable includes the path of *mymodule.py*!) -``@python`` ------------ +@python +------- -Seq programs can contain functions that will be executed by Python via ``pydef``: +Codon programs can contain functions that will be executed by Python via ``pydef``: -.. code-block:: seq +.. code-block:: python @python def multiply(a: int, b: int) -> int: @@ -56,7 +56,7 @@ Seq programs can contain functions that will be executed by Python via ``pydef`` This makes calling Python modules like NumPy very easy: -.. code-block:: seq +.. code-block:: python @python def myrange(n: int) -> List[int]: diff --git a/docs/sphinx/seqlex.py b/docs/sphinx/seqlex.py deleted file mode 100644 index fca1fe13..00000000 --- a/docs/sphinx/seqlex.py +++ /dev/null @@ -1,245 +0,0 @@ -# Seq Pygments lexer based on Python's - -import re - -from pygments.lexer import Lexer, RegexLexer, include, bygroups, using, \ - default, words, combined, do_insertions -from pygments.util import get_bool_opt, shebang_matches -from pygments.token import Text, Comment, Operator, Keyword, Name, String, \ - Number, Punctuation, Generic, Other, Error -from pygments import unistring as uni - -__all__ = ['SeqLexer'] - -line_re = re.compile('.*?\n') - -class SeqLexer(RegexLexer): - name = 'Seq' - aliases = ['seq'] - filenames = ['*.seq'] - mimetypes = [] - - flags = re.MULTILINE | re.UNICODE - - uni_name = "[%s][%s]*" % (uni.xid_start, uni.xid_continue) - - def innerstring_rules(ttype): - return [ - # the old style '%s' % (...) string formatting (still valid in Py3) - (r'%(\(\w+\))?[-#0 +]*([0-9]+|[*])?(\.([0-9]+|[*]))?' - '[hlL]?[E-GXc-giorsux%]', String.Interpol), - # the new style '{}'.format(...) string formatting - (r'\{' - '((\w+)((\.\w+)|(\[[^\]]+\]))*)?' # field name - '(\![sra])?' # conversion - '(\:(.?[<>=\^])?[-+ ]?#?0?(\d+)?,?(\.\d+)?[E-GXb-gnosx%]?)?' - '\}', String.Interpol), - - # backslashes, quotes and formatting signs must be parsed one at a time - (r'[^\\\'"%{\n]+', ttype), - (r'[\'"\\]', ttype), - # unhandled string formatting sign - (r'%|(\{{1,2})', ttype) - # newlines are an error (use "nl" state) - ] - - tokens = { - 'root': [ - (r'\n', Text), - (r'^(\s*)([rRuUbB]{,2})("""(?:.|\n)*?""")', - bygroups(Text, String.Affix, String.Doc)), - (r"^(\s*)([rRuUbB]{,2})('''(?:.|\n)*?''')", - bygroups(Text, String.Affix, String.Doc)), - (r'[^\S\n]+', Text), - (r'\A#!.+$', Comment.Hashbang), - (r'#.*$', Comment.Single), - (r'[]{}:(),;[]', Punctuation), - (r'\\\n', Text), - (r'\\', Text), - (r'(in|is|and|or|not)\b', Operator.Word), - (r'!=|==|<<|>>|[-~+/*%=<>&^|.]', Operator), - include('keywords'), - (r'(def)((?:\s|\\\s)+)', bygroups(Keyword, Text), 'funcname'), - (r'(class)((?:\s|\\\s)+)', bygroups(Keyword, Text), 'classname'), - (r'(from)((?:\s|\\\s)+)', bygroups(Keyword.Namespace, Text), - 'fromimport'), - (r'(import)((?:\s|\\\s)+)', bygroups(Keyword.Namespace, Text), - 'import'), - include('builtins'), - include('magicfuncs'), - include('magicvars'), - include('backtick'), - ('([skprR]|[uUbB][rR]|[rR][uUbB])(""")', - bygroups(String.Affix, String.Double), 'tdqs'), - ("([skprR]|[uUbB][rR]|[rR][uUbB])(''')", - bygroups(String.Affix, String.Single), 'tsqs'), - ('([skprR]|[uUbB][rR]|[rR][uUbB])(")', - bygroups(String.Affix, String.Double), 'dqs'), - ("([skprR]|[uUbB][rR]|[rR][uUbB])(')", - bygroups(String.Affix, String.Single), 'sqs'), - ('([uUbB]?)(""")', bygroups(String.Affix, String.Double), - combined('stringescape', 'tdqs')), - ("([uUbB]?)(''')", bygroups(String.Affix, String.Single), - combined('stringescape', 'tsqs')), - ('([uUbB]?)(")', bygroups(String.Affix, String.Double), - combined('stringescape', 'dqs')), - ("([uUbB]?)(')", bygroups(String.Affix, String.Single), - combined('stringescape', 'sqs')), - include('name'), - include('numbers'), - ], - 'funcname': [ - include('magicfuncs'), - ('[a-zA-Z_]\w*', Name.Function, '#pop'), - default('#pop'), - ], - 'stringescape': [ - (r'\\([\\abfnrtv"\']|\n|N\{.*?\}|u[a-fA-F0-9]{4}|' - r'U[a-fA-F0-9]{8}|x[a-fA-F0-9]{2}|[0-7]{1,3})', String.Escape) - ], - 'strings-single': innerstring_rules(String.Single), - 'strings-double': innerstring_rules(String.Double), - 'dqs': [ - (r'"', String.Double, '#pop'), - (r'\\\\|\\"|\\\n', String.Escape), # included here for raw strings - include('strings-double') - ], - 'sqs': [ - (r"'", String.Single, '#pop'), - (r"\\\\|\\'|\\\n", String.Escape), # included here for raw strings - include('strings-single') - ], - 'tdqs': [ - (r'"""', String.Double, '#pop'), - include('strings-double'), - (r'\n', String.Double) - ], - 'tsqs': [ - (r"'''", String.Single, '#pop'), - include('strings-single'), - (r'\n', String.Single) - ], - } - - tokens['keywords'] = [ - (words(( - 'assert', 'async', 'await', 'break', 'continue', 'del', 'elif', - 'else', 'except', 'finally', 'for', 'global', 'if', 'lambda', 'pass', - 'raise', 'nonlocal', 'return', 'try', 'while', 'yield', 'yield from', - 'as', 'with', 'match', 'case', 'pydef', - 'type', 'extend', 'print', 'cimport', 'pyimport'), suffix=r'\b'), - Keyword), - (words(( - 'True', 'False', 'None'), suffix=r'\b'), - Keyword.Constant), - ] - - seqwords = ['__import__', 'abs', 'all', 'any', 'bin', 'bool', 'bytearray', 'bytes', - 'chr', 'classmethod', 'cmp', 'compile', 'complex', 'delattr', 'dict', - 'dir', 'divmod', 'enumerate', 'eval', 'filter', 'float', 'format', - 'frozenset', 'getattr', 'globals', 'hasattr', 'hash', 'hex', 'id', - 'input', 'int', 'isinstance', 'issubclass', 'iter', 'len', 'list', - 'locals', 'map', 'max', 'memoryview', 'min', 'object', 'oct', - 'open', 'ord', 'pow', 'property', 'range', 'repr', 'reversed', - 'round', 'set', 'setattr', 'slice', 'sorted', 'staticmethod', 'str', - 'sum', 'super', 'tuple', 'vars', 'zip', 'seq', 'byte', 'ptr', 'array', - 'Kmer', 'Int', 'UInt', 'optional'] - - tokens['builtins'] = [ - (words(seqwords, prefix=r'(? add1 # 3; equivalent to add1(2) + + def calc(x, y): + return x + y**2 + 2 |> calc(3) # 11; equivalent to calc(2, 3) + 2 |> calc(..., 3) # 11; equivalent to calc(2, 3) + 2 |> calc(3, ...) # 7; equivalent to calc(3, 2) + + def gen(i): + for i in range(i): + yield i + + 5 |> gen |> print # prints 0 1 2 3 4 separated by newline + range(1, 4) |> iter |> gen |> print(end=' ') # prints 0 0 1 0 1 2 without newline + [1, 2, 3] |> print # prints [1, 2, 3] + range(100000000) |> print # prints range(0, 100000000) + range(100000000) |> iter |> print # not only prints all those numbers, but it uses almost no memory at all + +Codon will chain anything that implements ``__iter__``; however, use +generators as much as possible because the compiler will optimize out +generators whenever possible. Combinations of pipes and generators can be +used to implement efficient streaming pipelines. + +.. caution:: + The Codon compiler may perform optimizations that change the order of elements passed through a pipeline. Therefore, it is best to not rely on order when using pipelines. If order needs to be maintained, consider using a regular loop or passing an index alongside each element sent through the pipeline. + +Parallel Pipelines +------------------ + +CPython and many other implementations alike cannot take advantage of parallelism due to the infamous global interpreter lock, a mutex that protects accesses to Python objects, preventing multiple threads from executing Python bytecode at once. Unlike CPython, Codon has no such restriction and supports full multithreading. To this end, Codon supports a *parallel* pipe operator ``||>``, which is semantically similar to the standard pipe operator except that it allows the elements sent through it to be processed in parallel by the remainder of the pipeline. Hence, turning a serial program into a parallel one often requires the addition of just a single character in Codon. Further, a single pipeline can contain multiple parallel pipes, resulting in nested parallelism. + +.. code:: python + + range(100000) |> iter ||> print # prints all these numbers, probably in random order + range(100000) |> iter ||> process ||> clean # runs process in parallel, and then cleans data in parallel + +Codon will automatically schedule the ``process`` and ``clean`` functions to execute as soon as possible. You can control the number of threads via the ``OMP_NUM_THREADS`` environment variable. + +Internally, the Codon compiler uses an OpenMP task backend to generate code for parallel pipelines. Logically, parallel pipe operators are similar to parallel-for loops: the portion of the pipeline after the parallel pipe is outlined into a new function that is called by the OpenMP runtime task spawning routines (as in ``#pragma omp task`` in C++), and a synchronization point (``#pragma omp taskwait``) is added after the outlined segment. Lastly, the entire program is implicitly placed in an OpenMP parallel region (``#pragma omp parallel``) that is guarded by a "single" directive (``#pragma omp single``) so that the serial portions are still executed by one thread (this is required by OpenMP as tasks must be bound to an enclosing parallel region). diff --git a/docs/sphinx/tutorial/primer.rst b/docs/sphinx/tutorial/primer.rst index 8bd25fc1..e814432e 100644 --- a/docs/sphinx/tutorial/primer.rst +++ b/docs/sphinx/tutorial/primer.rst @@ -1,14 +1,14 @@ Language Primer =============== -If you know Python, you already know 95% of Seq. The following primer +If you know Python, you already know 95% of Codon. The following primer assumes some familiarity with Python or at least one "modern" programming language (QBASIC doesn't count). Printing -------- -.. code:: seq +.. code:: python print('hello world') @@ -18,9 +18,9 @@ Printing Comments -------- -.. code:: seq +.. code:: python - # Seq comments start with "# 'and go until the end of the line + # Codon comments start with "# 'and go until the end of the line """ There are no multi-line comments. You can (ab)use the docstring operator (''') @@ -30,10 +30,10 @@ Comments Literals -------- -Seq is a strongly typed language like C++, Java, or C#. That means each +Codon is a strongly typed language like C++, Java, or C#. That means each expression must have a type that can be inferred at the compile-time. -.. code:: seq +.. code:: python # Booleans True # type: bool @@ -41,7 +41,7 @@ expression must have a type that can be inferred at the compile-time. # Numbers a = 1 # type: int. It's 64-bit signed integer. - b = 1.12 # type: float. Seq's float is identical to C's double. + b = 1.12 # type: float. Codon's float is identical to C's double. c = 5u # type: int, but unsigned d = Int[8](12) # 8-bit signed integer; you can go all the way to Int[2048] e = UInt[8](200) # 8-bit unsigned integer @@ -68,15 +68,10 @@ expression must have a type that can be inferred at the compile-time. # \\, \', \", \a, \b, \f, \n, \r, \t, \v, # \xHHH (HHH is hex code), \OOO (OOO is octal code) - # Sequence types - dna = s"ACGT" # type: seq. These are DNA sequences. - prt = p"MYX" # type: bio.pseq. These are protein sequences. - kmer = k"ACGT" # type: Kmer[4]. Note that Kmer[5] is different than Kmer[12]. - Tuples ~~~~~~ -.. code:: seq +.. code:: python # Tuples t = (1, 2.3, 'hi') # type: Tuple[int, float, str]. @@ -87,10 +82,10 @@ As all types must be known at compile time, tuple indexing works only if a tuple is homogenous (all types are the same) or if the value of the index is known at compile-time. -You can, however, iterate over heterogenous tuples in Seq. This is achieved +You can, however, iterate over heterogenous tuples in Codon. This is achieved by unrolling the loop to accommodate the different types. -.. code:: seq +.. code:: python t = (1, 2.3, 'hi') t[1] # works because 1 is a constant int @@ -116,7 +111,7 @@ by unrolling the loop to accommodate the different types. Containers ~~~~~~~~~~ -.. code:: seq +.. code:: python l = [1, 2, 3] # type: List[int]; a list of integers s = {1.1, 3.3, 2.2, 3.3} # type: Set[float]; a set of floats @@ -127,9 +122,9 @@ Containers dn = {} # an empty dict whose type is inferred based on usage dn = Dict[int, float]() # an empty dictionary with explicit element types -Because Seq is strongly typed, these won't compile: +Because Codon is strongly typed, these won't compile: -.. code:: seq +.. code:: python l = [1, 's'] # is it a List[int] or List[str]? you cannot mix-and-match types d = {1: 'hi'} @@ -138,11 +133,11 @@ Because Seq is strongly typed, these won't compile: t = (1, 2.2) # Tuple[int, float] lt = list(t) # compile error: t is not homogenous - lp = [1, 2.1, 3, 5] # compile error: Seq will not automatically cast a float to an int + lp = [1, 2.1, 3, 5] # compile error: Codon will not automatically cast a float to an int This will work, though: -.. code:: seq +.. code:: python u = (1, 2, 3) lu = list(u) # works: u is homogenous @@ -156,7 +151,7 @@ This will work, though: Assignments and operators ------------------------- -.. code:: seq +.. code:: python a = 1 + 2 # this is 3 a = (1).__add__(2) # you can use a function call instead of an operator; this is also 3 @@ -178,7 +173,6 @@ Operator Magic method Description ``**`` ``__pow__`` exponentiation ``%`` ``__mod__`` modulo ``@`` ``__matmul__`` matrix multiplication; - sequence alignment ``&`` ``__and__`` bitwise and ``|`` ``__or__`` bitwise or ``^`` ``__xor__`` bitwise xor @@ -195,7 +189,7 @@ Operator Magic method Description ``or`` none boolean or (short-circuits) ======== ================ ================================================== -Seq also has the following unary operators: +Codon also has the following unary operators: ======== ================ ============================= Operator Magic method Description @@ -211,9 +205,9 @@ Operator Magic method Description Tuple unpacking ~~~~~~~~~~~~~~~ -Seq supports most of Python's tuple unpacking syntax: +Codon supports most of Python's tuple unpacking syntax: -.. code:: seq +.. code:: python x, y = 1, 2 # x is 1, y is 2 (x, (y, z)) = 1, (2, 3) # x is 1, y is 2, z is 3 @@ -240,9 +234,9 @@ Control flow Conditionals ~~~~~~~~~~~~ -Seq supports the standard Python conditional syntax: +Codon supports the standard Python conditional syntax: -.. code:: seq +.. code:: python if a or b or some_cond(): print(1) @@ -255,10 +249,10 @@ Seq supports the standard Python conditional syntax: a = b if sth() else c # ternary conditional operator -Seq extends the Python conditional syntax with a ``match`` statement, which is +Codon extends the Python conditional syntax with a ``match`` statement, which is inspired by Rust's: -.. code:: seq +.. code:: python match a + some_heavy_expr(): # assuming that the type of this expression is int case 1: # is it 1? @@ -300,12 +294,6 @@ inspired by Rust's: case [...]: # any other list ... - match sequence: # of type seq - case 'ACGT': ... - case 'AC_T': ... # _ is a wildcard character and it can be anything - case 'A_C_T_': ... # a spaced k-mer AxCxTx - case 'AC*T': ... # matches a sequence that starts with AC and ends with T - You can mix, match and chain match rules as long as the match type matches the expression type. @@ -314,7 +302,7 @@ Loops Standard fare: -.. code:: seq +.. code:: python a = 10 while a > 0: # prints even numbers from 9 to 1 @@ -340,7 +328,7 @@ Comprehensions Technically, comprehensions are not statements (they are expressions). Comprehensions are a nifty, Pythonic way to create collections: -.. code:: seq +.. code:: python l = [i for i in range(5)] # type: List[int]; l is [0, 1, 2, 3, 4] l = [i for i in range(15) if i % 2 == 1 if i > 10] # type: List[int]; l is [11, 13] @@ -352,7 +340,7 @@ Comprehensions are a nifty, Pythonic way to create collections: You can also use collections to create generators (more about them later on): -.. code:: seq +.. code:: python g = (i for i in range(10)) print(list(g)) # prints number from 0 to 9, inclusive @@ -361,9 +349,9 @@ Exception handling ~~~~~~~~~~~~~~~~~~ Again, if you know how to do this in Python, you know how to do it in -Seq: +Codon: -.. code:: seq +.. code:: python def throwable(): raise ValueError("doom and gloom") @@ -378,14 +366,14 @@ Seq: print("whatever, it's done") .. note:: - Right now, Seq cannot catch multiple exceptions in one + Right now, Codon cannot catch multiple exceptions in one statement. Thus ``catch (Exc1, Exc2, Exc3) as var`` will not compile. If you have an object that implements ``__enter__`` and ``__exit__`` methods to manage its lifetime (say, a ``File``), you can use a ``with`` statement to make your life easy: -.. code:: seq +.. code:: python with open('foo.txt') as f, open('foo_copy.txt', 'w') as fo: for l in f: @@ -394,20 +382,20 @@ statement to make your life easy: Variables and scoping --------------------- -You have probably noticed by now that blocks in Seq are defined by their +You have probably noticed by now that blocks in Codon are defined by their indentation level (as in Python). We recommend using 2 or 4 spaces to indent blocks. Do not mix indentation levels, and do not mix tabs and spaces; stick to any *consistent* way of indenting your code. -One of the major differences between Seq and Python lies in variable -scoping rules. Seq variables cannot *leak* to outer blocks. Every +One of the major differences between Codon and Python lies in variable +scoping rules. Codon variables cannot *leak* to outer blocks. Every variable is accessible only within its own block (after the variable is defined, of course), and within any block that is nested within the variable's own block. That means that the following Pythonic pattern won't compile: -.. code:: seq +.. code:: python if cond(): x = 1 @@ -419,9 +407,9 @@ That means that the following Pythonic pattern won't compile: ... print(i) # error: i is only accessible within the for loop block -In Seq, you can rewrite that as: +In Codon, you can rewrite that as: -.. code:: seq +.. code:: python x = 2 if cond(): @@ -432,10 +420,10 @@ In Seq, you can rewrite that as: print(x) -Another important difference between Seq and Python is that, in Seq, variables +Another important difference between Codon and Python is that, in Codon, variables cannot change types. So this won't compile: -.. code:: seq +.. code:: python a = 's' a = 1 # error: expected string, but got int @@ -444,7 +432,7 @@ A note about function scoping: functions cannot modify variables that are not defined within the function block. You need to use ``global`` to modify such variables: -.. code:: seq +.. code:: python g = 5 def foo(): @@ -468,24 +456,24 @@ are not defined within the function. Imports ------- -You can import functions and classes from another Seq module by doing: +You can import functions and classes from another Codon module by doing: -.. code:: seq +.. code:: python - # Create foo.seq with a bunch of useful methods + # Create foo.codon with a bunch of useful methods import foo foo.useful1() p = foo.FooType() - # Create bar.seq with a bunch of useful methods + # Create bar.codon with a bunch of useful methods from bar import x, y x(y) from bar import z as bar_z bar_z() -``import foo`` looks for ``foo.seq`` or ``foo/__init__.seq`` in the +``import foo`` looks for ``foo.codon`` or ``foo/__init__.codon`` in the current directory. Functions @@ -493,7 +481,7 @@ Functions Functions are defined as follows: -.. code:: seq +.. code:: python def foo(a, b, c): return a + b + c @@ -501,7 +489,7 @@ Functions are defined as follows: How about procedures? Well, don't return anything meaningful: -.. code:: seq +.. code:: python def proc(a, b): print(a, 'followed by', b) @@ -514,10 +502,10 @@ How about procedures? Well, don't return anything meaningful: proc2(1, 's') proc2(5, 's') # this prints nothing -Seq is a strongly-typed language, so you can restrict argument and +Codon is a strongly-typed language, so you can restrict argument and return types: -.. code:: seq +.. code:: python def fn(a: int, b: float): return a + b # this works because int implements __add__(float) @@ -538,7 +526,7 @@ return types: Default arguments? Named arguments? You bet: -.. code:: seq +.. code:: python def foo(a, b: int, c: float = 1.0, d: str = 'hi'): print(a, b, c, d) @@ -547,7 +535,7 @@ Default arguments? Named arguments? You bet: How about optional arguments? We support that too: -.. code:: seq +.. code:: python # type of b promoted to Optional[int] def foo(a, b: int = None): @@ -559,29 +547,29 @@ How about optional arguments? We support that too: Generics ~~~~~~~~ -As we've said several times: Seq is a strongly typed language. As +As we've said several times: Codon is a strongly typed language. As such, it is not as flexible as Python when it comes to types (e.g. you can't have lists with elements of different types). However, -Seq tries to mimic Python's *"I don't care about types until I do"* +Codon tries to mimic Python's *"I don't care about types until I do"* attitude as much as possible by utilizing a technique known as *monomorphization*. If there is a function that has an argument -without a type definition, Seq will consider it a *generic* function, +without a type definition, Codon will consider it a *generic* function, and will generate different functions for each invocation of that generic function: -.. code:: seq +.. code:: python def foo(x): print(x) # print relies on typeof(x).__str__(x) method to print the representation of x - foo(1) # Seq automatically generates foo(x: int) and calls int.__str__ when needed - foo('s') # Seq automatically generates foo(x: str) and calls str.__str__ when needed - foo([1, 2]) # Seq automatically generates foo(x: List[int]) and calls List[int].__str__ when needed + foo(1) # Codon automatically generates foo(x: int) and calls int.__str__ when needed + foo('s') # Codon automatically generates foo(x: str) and calls str.__str__ when needed + foo([1, 2]) # Codon automatically generates foo(x: List[int]) and calls List[int].__str__ when needed But what if you need to mix type definitions and generic types? Say, your function can take a list of *anything*? Well, you can use generic specifiers: -.. code:: seq +.. code:: python def foo(x: List[T], T: type): print(x) @@ -604,9 +592,9 @@ specifiers: Generators ~~~~~~~~~~ -Seq supports generators, and they are fast! Really, really fast! +Codon supports generators, and they are fast! Really, really fast! -.. code:: seq +.. code:: python def gen(i): while i < 10: @@ -619,7 +607,7 @@ You can also use ``yield`` to implement coroutines: ``yield`` suspends the function, while ``(yield)`` (yes, parentheses are required) receives a value, as in Python. -.. code:: seq +.. code:: python def mysum[T](start: T): m = start @@ -635,62 +623,16 @@ receives a value, as in Python. iadder.send(i) # send a value to coroutine print(iadder.send(-1)) # prints 45 -Pipelines -~~~~~~~~~ - -Seq extends the core Python language with a pipe operator, which is -similar to bash pipes (or F#'s ``|>`` operator). You can chain multiple -functions and generators to form a pipeline: - -.. code:: seq - - def add1(x): - return x + 1 - - 2 |> add1 # 3; equivalent to add1(2) - - def calc(x, y): - return x + y**2 - 2 |> calc(3) # 11; equivalent to calc(2, 3) - 2 |> calc(..., 3) # 11; equivalent to calc(2, 3) - 2 |> calc(3, ...) # 7; equivalent to calc(3, 2) - - def gen(i): - for i in range(i): - yield i - 5 |> gen |> print # prints 0 1 2 3 4 separated by newline - range(1, 4) |> iter |> gen |> print(end=' ') # prints 0 0 1 0 1 2 without newline - [1, 2, 3] |> print # prints [1, 2, 3] - range(100000000) |> print # prints range(0, 100000000) - range(100000000) |> iter |> print # not only prints all those numbers, but it uses almost no memory at all - -Seq will chain anything that implements ``__iter__``; however, use -generators as much as possible because the compiler will optimize out -generators whenever possible. Combinations of pipes and generators can be -used to implement efficient streaming pipelines. - -Seq can also execute pipelines in parallel via the parallel pipe (``||>``) -operator: - -.. code:: seq - - range(100000) |> iter ||> print # prints all these numbers, probably in random order - range(100000) |> iter ||> process ||> clean # runs process in parallel, and then cleans data in parallel - -In the last example, Seq will automatically schedule the ``process`` and -``clean`` functions to execute as soon as possible. You can control the -number of threads via the ``OMP_NUM_THREADS`` environment variable. - .. _interop: Foreign function interface (FFI) ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Seq can easily call functions from C and Python. +Codon can easily call functions from C and Python. Let's import some C functions: -.. code:: seq +.. code:: python from C import pow(float) -> float pow(2.0) # 4.0 @@ -698,15 +640,15 @@ Let's import some C functions: # Import and rename function from C import puts(cobj) -> void as print_line # type cobj is C's pointer (void*, char*, etc.) print_line("hi!".c_str()) # prints "hi!". - # Note .ptr at the end of string--- needed to cast Seq's string to char*. + # Note .ptr at the end of string--- needed to cast Codon's string to char*. ``from C import`` only works if the symbol is available to the program. If you -are running your programs via ``seqc``, you can link dynamic libraries -by running ``seqc run -l path/to/dynamic/library.so ...``. +are running your programs via ``codon``, you can link dynamic libraries +by running ``codon run -l path/to/dynamic/library.so ...``. Hate linking? You can also use dyld library loading as follows: -.. code:: seq +.. code:: python LIBRARY = "mycoollib.so" @@ -716,21 +658,21 @@ Hate linking? You can also use dyld library loading as follows: foo2 = my2(4, 3.2) .. note:: - When importing external non-Seq functions, you must explicitly specify + When importing external non-Codon functions, you must explicitly specify argument and return types. -How about Python? If you have set the ``SEQ_PYTHON`` environment variable as +How about Python? If you have set the ``CODON_PYTHON`` environment variable as described in the first section, you can do: -.. code:: seq +.. code:: python from python import mymodule.myfunction(str) -> int as foo print(foo("bar")) -Often you want to execute more complex Python code within Seq. To that -end, you can use Seq's ``@python`` annotation: +Often you want to execute more complex Python code within Codon. To that +end, you can use Codon's ``@python`` annotation: -.. code:: seq +.. code:: python @python def scipy_here_i_come(i: List[List[float]]) -> List[float]: @@ -743,18 +685,18 @@ end, you can use Seq's ``@python`` annotation: return list(eigenvalues) print(scipy_here_i_come([[1.0, 2.0], [3.0, 4.0]])) # [-0.372281, 5.37228] with some warnings... -Seq will automatically bridge any object that implements the ``__to_py__`` -and ``__from_py__`` magic methods. All standard Seq types already +Codon will automatically bridge any object that implements the ``__to_py__`` +and ``__from_py__`` magic methods. All standard Codon types already implement these methods. Classes and types ----------------- -Of course, Seq supports classes! However, you must declare class members +Of course, Codon supports classes! However, you must declare class members and their types in the preamble of each class (like you would do with Python's dataclasses). -.. code:: seq +.. code:: python class Foo: x: int @@ -770,11 +712,11 @@ Python's dataclasses). f.method() # prints "1 2" .. note:: - Seq does not (yet!) support inheritance and polymorphism. + Codon does not (yet!) support inheritance and polymorphism. -Unlike Python, Seq supports method overloading: +Unlike Python, Codon supports method overloading: -.. code:: seq +.. code:: python class Foo: x: int @@ -799,7 +741,7 @@ Unlike Python, Seq supports method overloading: Classes can also be generic: -.. code:: seq +.. code:: python class Container[T]: l: List[T] @@ -809,7 +751,7 @@ Classes can also be generic: Classes create objects that are passed by reference: -.. code:: seq +.. code:: python class Point: x: int @@ -824,9 +766,9 @@ Classes create objects that are passed by reference: If you need to copy an object's contents, implement the ``__copy__`` magic method and use ``q = copy(p)`` instead. -Seq also supports pass-by-value types via the ``@tuple`` annotation: +Codon also supports pass-by-value types via the ``@tuple`` annotation: -.. code:: seq +.. code:: python @tuple class Point: @@ -840,7 +782,7 @@ Seq also supports pass-by-value types via the ``@tuple`` annotation: However, **by-value objects are immutable!**. The following code will not compile: -.. code:: seq +.. code:: python p = Point(1, 2) p.x = 2 # error! immutable type @@ -850,7 +792,7 @@ Under the hood, types are basically named tuples (equivalent to Python's You can also add methods to types: -.. code:: seq +.. code:: python @tuple class Point: @@ -869,17 +811,16 @@ You can also add methods to types: Type extensions ~~~~~~~~~~~~~~~ -Suppose you have a class that lacks a method or an operator that might -be really useful. You can extend that class and add the method at compile time: +Suppose you have a class that lacks a method or an operator that might be really useful. Codon provides an ``@extend`` annotation that allows you to add and modify methods of various types at compile time, including built-in types like ``int`` or ``str``. This allows much of the functionality of built-in types to be implemented in Codon as type extensions in the standard library. -.. code:: seq +.. code:: python class Foo: ... f = Foo(...) - # we need foo.cool() but it does not exist... not a problem for Seq + # We need foo.cool() but it does not exist... not a problem for Codon @extend class Foo: def cool(self: Foo): @@ -887,14 +828,16 @@ be really useful. You can extend that class and add the method at compile time: f.cool() # works! - # how about we add support for adding integers and strings? + # How about we add support for adding integers and strings: @extend class int: - def __add__(self: int, other: str) -> int: + def __add__(self: int, other: str): return self + int(other) print(5 + '4') # 9 +Note that all type extensions are performed strictly at compile time and incur no runtime overhead. + Magic methods ~~~~~~~~~~~~~ @@ -915,13 +858,22 @@ operators overload unary and binary operators (see :ref:`operators`) ``__str__`` support printing and ``str`` method ================ ============================================= +Other types +~~~~~~~~~~~ + +Codon provides arbitrary-width signed and unsigned integers, e.g. ``Int[32]`` is a signed 32-bit integer while ``UInt[128]`` is an unsigned 128-bit integer, respectively (note that ``int`` is an ``Int[64]``). Typedefs for common bit widths are provided in the standard library, such as ``i8``, ``i16``, ``u32``, ``u64`` etc. + +The ``Ptr[T]`` type in Codon also corresponds to a raw C pointer (e.g. ``Ptr[byte]`` is equivalent to ``char*`` in C). The ``Array[T]`` type represents a fixed-length array (essentially a pointer with a length). + +Codon also provides ``__ptr__`` for obtaining a pointer to a variable (as in ``__ptr__(myvar)``) and ``__array__`` for declaring stack-allocated arrays (as in ``__array__[int](10)``). + LLVM functions ~~~~~~~~~~~~~~ In certain cases, you might want to use LLVM features that are not directly -accessible with Seq. This can be done with the ``@llvm`` attribute: +accessible with Codon. This can be done with the ``@llvm`` attribute: -.. code:: seq +.. code:: python @llvm def llvm_add[T](a: T, b: T) -> T: @@ -933,4 +885,4 @@ accessible with Seq. This can be done with the ``@llvm`` attribute: -------------- -Issues, feedback, or comments regarding this tutorial? Let us know `on GitHub `__. +Issues, feedback, or comments regarding this tutorial? Let us know `on GitHub `__. diff --git a/docs/sphinx/tutorial/setup.rst b/docs/sphinx/tutorial/setup.rst index 94812078..e13a7350 100644 --- a/docs/sphinx/tutorial/setup.rst +++ b/docs/sphinx/tutorial/setup.rst @@ -11,22 +11,22 @@ Simple! /bin/bash -c "$(curl -fsSL https://seq-lang.org/install.sh)" If you want to use Python interop, you also need to point -``SEQ_PYTHON`` to the Python library (typically called -``libpython3.9m.so`` or similar). The Seq repository contains a -`Python script `_ +``CODON_PYTHON`` to the Python library (typically called +``libpython3.9m.so`` or similar). The Codon repository contains a +`Python script `_ that will identify and print the path to this library. Usage ----- -Assuming that Seq was properly installed, you can use it as follows: +Assuming that Codon was properly installed, you can use it as follows: .. code:: bash - seqc run foo.seq # Compile and run foo.seq - seqc run -release foo.seq # Compile and run foo.seq with optimizations - seqc build -exe file.seq # Compile foo.seq to executable "foo" + codon run foo.codon # Compile and run foo.codon + codon run -release foo.codon # Compile and run foo.codon with optimizations + codon build -exe file.codon # Compile foo.codon to executable "foo" Note that the ``-exe`` option requires ``clang`` to be installed, and -the ``LIBRARY_PATH`` environment variable to point to the Seq runtime -library (installed by default at ``~/.seq/lib/seq``). +the ``LIBRARY_PATH`` environment variable to point to the Codon runtime +library (installed by default at ``~/.codon/lib/codon``). diff --git a/docs/sphinx/tutorial/tutorial.rst b/docs/sphinx/tutorial/tutorial.rst deleted file mode 100644 index 320d1e0d..00000000 --- a/docs/sphinx/tutorial/tutorial.rst +++ /dev/null @@ -1,411 +0,0 @@ -Tutorial -======== - -Bio-specific features ---------------------- - -Seq's ``bio`` module contains all the following functions, types, and methods. The code snippets below should be preceded with ``from bio import *``, although we omit that line for simplicity below. - -Genomic types -^^^^^^^^^^^^^ - -Seq's namesake type is indeed the sequence type: ``seq``. A ``seq`` object represents a DNA sequence of any length and---on top of general-purpose string functionality---provides methods for performing common sequence operations such as splitting into subsequences, reverse complementation and :math:`k`-mer extraction. Alongside the ``seq`` type are :math:`k`-mer types, where e.g. ``Kmer[1]`` represents a 1-mer, ``Kmer[2]`` a 2-mer and so on, up to ``Kmer[1024]``. - -Sequences can be seamlessly converted between these various types: - -.. code-block:: seq - - dna = s'ACGTACGTACGT' # sequence literal - - # (a) split into subsequences of length 3 - # with a step of 2 - for sub in dna.split(k=3, step=2): - print(sub) - print(~sub) # reverse complement - - # (b) split into 5-mers with step 1 (default) - for kmer in dna.kmers(k=5): - print(kmer) - print(~kmer) # reverse complement - - # (c) convert entire sequence to 12-mer - kmer = Kmer[12](dna) - -Seq also supports a ``pseq`` type for protein sequences: - -.. code-block:: seq - - protein = p'HEAGAWGHE' # pseq literal - print(list(protein.split(3, 3))) # [HEA, GAW, GHE] - print(s'ACCATGACA' |> translate) # TMT - -.. Note:: What's the difference between sequences and :math:`k`-mers in Seq? Sequences have arbitrary length and allow for ambiguous bases like ``N``. :math:`k`-mers, on the other hand, have a length that is fixed and must be known at compile time, only allowing for ``ACGT`` bases. :math:`k`-mers can therefore be represented internally as 2-bit encoded integers, making them compact and very efficient to manipulate. - -In practice, sequences would be read from e.g. a FASTQ file: - -.. code-block:: seq - - for record in FASTQ('input.fq'): - print('processing', record.name) - process(record.seq) - -If you only care about the sequences, you can also do this: - -.. code-block:: seq - - for read in FASTQ('input.fq') |> seqs: - process(read) - -Common formats like FASTQ, FASTA, SAM, BAM and CRAM are supported. The ``FASTQ`` and ``FASTA`` parsers support several additional options: - -- ``validate`` (``True`` by default): Perform data validation as sequences are read -- ``gzip`` (``True`` by default): Perform I/O using zlib, supporting gzip'd files (note that plain text files will still work with this enabled) -- ``fai`` (``True`` by default; FASTA only): Look for a ``.fai`` file to determine sequence lengths before reading - -For example: - -.. code-block:: seq - - for read in FASTQ('input.fq', validate=False, gzip=False) |> seqs: - process(read) - -To read protein sequences, you can use ``pFASTA``, which has the same interface as ``FASTA`` (but does not support ``fai``): - -.. code-block:: seq - - for p in pFASTA('input.fa') |> seqs: - process(p) - -.. _match: - -Sequence matching -^^^^^^^^^^^^^^^^^ - -Seq provides the conventional ``match`` construct, which works on integers, lists, strings and tuples. Here's a simple example: - -.. code-block:: seq - - def describe(n: int): - match n: - case m if m < 0: - print('negative') - case 0: - print('zero') - case m if 0 < m < 10: - print('small') - case _: - print('large') - -A novel aspect of Seq's ``match`` statement is that it also works on sequences, and allows for concise recursive representations of several sequence operations such as subsequence search, reverse complementation tests and base counting, as shown in this example: - -.. code-block:: seq - - # (a) - def has_spaced_acgt(s: seq): - match s: - case 'A_C_G_T*': - return True - case t if len(t) >= 8: - return has_spaced_acgt(s[1:]) - case _: - return False - - # (b) - def is_own_revcomp(s: seq): - match s: - case 'A*T' or 'T*A' or 'C*G' or 'G*C': - return is_own_revcomp(s[1:-1]) - case s'': - return True - case _: - return False - - # (c) - @tuple - class BaseCount: - A: int - C: int - G: int - T: int - - def __add__(self, other: BaseCount): - a1, c1, g1, t1 = self - a2, c2, g2, t2 = other - return (a1 + a2, c1 + c2, g1 + g2, t1 + t2) - - def count_bases(s): - match s: - case 'A*': return count_bases(s[1:]) + (1,0,0,0) - case 'C*': return count_bases(s[1:]) + (0,1,0,0) - case 'G*': return count_bases(s[1:]) + (0,0,1,0) - case 'T*': return count_bases(s[1:]) + (0,0,0,1) - case _: return BaseCount(0,0,0,0) - -- Example (a) checks if a given sequence contains the subsequence ``A_C_G_T``, where ``_`` is a wildcard base. -- Example (b) checks if the given sequence is its own reverse complement. -- Example (c) counts how many times each base appears in the given sequence. - -Sequence patterns consist of literal ``ACGT`` characters, single-base wildcards (``_``) or "zero or more" wildcards (``...``) that match zero or more of any base. - -.. _pipeline: - -Pipelines -^^^^^^^^^ - -Pipelining is a natural model for thinking about processing genomic data, as sequences are typically processed in stages (e.g. read from input file, split into :math:`k`-mers, query :math:`k`-mers in index, perform full dynamic programming alignment, output results to file), and are almost always independent of one another as far as this processing is concerned. Because of this, Seq supports a pipe operator: ``|>``, similar to F#'s pipe and R's ``magrittr`` (``%>%``). - -Pipeline stages in Seq can be regular functions or generators. In the case of standard functions, the function is simply applied to the input data and the result is carried to the remainder of the pipeline, akin to F#'s functional piping. If, on the other hand, a stage is a generator, the values yielded by the generator are passed lazily to the remainder of the pipeline, which in many ways mirrors how piping is implemented in Bash. Note that Seq ensures that generator pipelines do not collect any data unless explicitly requested, thus allowing the processing of terabytes of data in a streaming fashion with no memory and minimal CPU overhead. - -Here's an example of pipeline usage, which shows the same two loops from above, but as pipelines: - -.. code-block:: seq - - dna = s'ACGTACGTACGT' # sequence literal - - # (a) split into subsequences of length 3 - # with a stride of 2 - dna |> split(..., k=3, step=2) |> print - - # (b) split into 5-mers with stride 1 - def f(kmer): - print(kmer) - print(~kmer) - - dna |> kmers(k=5, step=1) |> f - -First, note that ``split`` is a Seq standard library function that takes three arguments: the sequence to split, the subsequence length and the stride; ``split(..., k=3, step=2)`` is a partial call of ``split`` that produces a new single-argument function ``f(x)`` which produces ``split(x, k=3, step=2)``. The undefined argument(s) in a partial call can be implicit, as in the second example: ``kmers`` (also a standard library function) is parameterized by the target :math:`k`-mer type and takes as arguments the sequence to :math:`k`-merize, the :math:`k`-mer length, and the stride; since just two of the three arguments are provided, the first is implicitly replaced by ``...`` to produce a partial call (i.e. the expression is equivalent to ``kmers(..., k=5, step=1)``). Both ``split`` and ``kmers`` are themselves generators that yield subsequences and :math:`k`-mers respectively, which are passed sequentially to the last stage of the enclosing pipeline in the two examples. - -.. caution:: - The Seq compiler may perform optimizations that change the order of elements passed through a pipeline. Therefore, it is best to not rely on order when using pipelines. If order needs to be maintained, consider using a regular loop or passing an index alongside each element sent through the pipeline. - -Sequence alignment -^^^^^^^^^^^^^^^^^^ - -Aligning sequences is very straightforward in Seq, and supports numerous options/variants: - -.. code-block:: seq - - # default parameters - s1 = s'CGCGAGTCTT' - s2 = s'CGCAGAGTT' - aln = s1 @ s2 - print(aln.cigar, aln.score) - - # custom parameters - # match = 2; mismatch = 4; gap1(k) = 2k + 4; gap2(k) = k + 13 - aln = s1.align(s2, a=2, b=4, gapo=4, gape=2, gapo2=13, gape2=1) - print(aln.cigar, aln.score) - -Here is the list of options supported by the ``align()`` method; all are optional (default is global alignment): - -- ``a``: match score -- ``b``: mismatch score -- ``ambig``: ambiguous (i.e. N) match score -- ``gapo``: gap open cost -- ``gape``: gap extension cost -- ``gapo2``: 2nd gap open cost for dual gap cost function -- ``gape2``: 2nd gap extension cost for dual gap cost function -- ``bandwidth``: bandwidth for DP alignment -- ``zdrop``: off-diagonal drop-off to stop extension -- ``score_only``: if true, don't compute CIGAR -- ``right``: if true, right-align gaps -- ``approx_max``: if true, approximate max -- ``approx_drop``: if true, approximate Z-drop -- ``rev_cigar``: if true, reverse CIGAR in output -- ``ext_only``: if true, perform extension alignment -- ``splice``: if true, perform spliced alignment - -Note that all costs/scores are positive by convention. - -.. _interalign: - -Inter-sequence alignment -"""""""""""""""""""""""" - -Seq uses `ksw2 `_ as its default alignment kernel. ksw2 does a good job of applying SIMD parallelization to align a single pair of sequences, which is referred to as *intra-sequence* alignment. However, we can often get better performance by aligning multiple sequences at once, referred to as *inter-sequence* alignment. Inter-sequence alignment is usually more cumbersome to program in general-purpose languages because many sequences need to be batched before performing the alignment. However, in Seq, inter-sequence alignment is as easy as intra-sequence, using the ``@inter_align`` annotation: - -.. code-block:: seq - - @inter_align - def process(t): - query, target = t - score = query.align(target, a=1, b=2, ambig=0, gapo=2, gape=1, zdrop=100, bandwidth=100, end_bonus=5) - print(query, target, score) - - zip(seqs('queries.txt'), seqs('targets.txt')) |> process - -Internally, the Seq compiler performs pipeline transformations when sequence alignment is performed within a function tagged ``@inter_align``, so as to suspend execution of the calling function, batch sequences that need to be aligned, perform inter-sequence alignment and return the results to the suspended functions. Note that the inter-sequence alignment kernel used by Seq is adapted from `BWA-MEM2 `_. - -.. _prefetch: - -Genomic index prefetching -^^^^^^^^^^^^^^^^^^^^^^^^^ - -Large genomic indices---ranging from several to tens or even hundreds of gigabytes---used in many applications result in extremely poor cache performance and, ultimately, a substantial fraction of stalled memory-bound cycles. For this reason, Seq performs pipeline optimizations to enable data prefetching and to hide memory latencies. You, the user, must provide just: - -- a ``__prefetch__`` magic method definition in the index class, which is logically similar to ``__getitem__`` (indexing construct) but performs a prefetch instead of actually loading the requested value (and can simply delegate to ``__prefetch__`` methods of built-in types); -- a one-line ``@prefetch`` annotation on functions that should perform prefetching. - -In particular, a typical prefetch-friendly index class would look like this: - -.. code-block:: seq - - class MyIndex: # abstract k-mer index - ... - def __getitem__(self, kmer: Kmer[20]): - # standard __getitem__ - def __prefetch__(self, kmer: Kmer[20]): - # similar to __getitem__, but performs prefetch - -Now, if we were to process data in a pipeline as such: - -.. code-block:: seq - - @prefetch - def process(read: seq, index: MyIndex): - ... - for kmer in read.kmers(k=20, step=step): - hits_fwd = index[kmer] - hits_rev = index[~kmer] - ... - return x - - FASTQ("reads.fq") |> seqs |> process(index) |> postprocess - -The Seq compiler will perform pipeline transformations to overlap cache misses in ``MyIndex`` with other useful work, increasing overall throughput. In our benchmarks, we often find these transformations to improve performance by 50% to 2×. However, the improvement is dataset- and application-dependent (and can potentially even decrease performance, although we rarely observed this), so users are encouraged to experiment with it for their own use case. - -As a concrete example, consider Seq's built-in FM-index type, ``FMIndex``, and a toy application that counts occurences of 20-mers from an input FASTQ. ``FMIndex`` provides end-to-end search methods like ``locate()`` and ``count()``, but we can take advantage of Seq's prefetch optimization by working with FM-index intervals: - -.. code-block:: seq - - from bio.fmindex import FMIndex - - fmi = FMIndex('/path/to/genome.fa') - k, step, n = 20, 20, 0 - - def update(count: int): - global n - n += count - - @prefetch - def find(s: seq, fmi: FMIndex): - intv = fmi.interval(s[-1]) # initial FM-index interval - s = s[:-1] # trim off last base of sequence - while s and intv: - intv = fmi[intv, s[-1]] # backwards extend FM-index interval - s = s[:-1] # trim off last base of sequence - return len(intv) # return count of sequence in index - - FASTQ('/path/to/reads.fq') |> seqs |> split(k, step) |> find(fmi) |> update - print('total:', n) - -That single ``@prefetch`` line can have a significant impact, especially for larger ``k``. Here is a graph of the performance of this exact snippet for various ``k`` using hg19 as the reference: - -.. image:: ../../images/prefetch.png - :width: 500px - :align: center - :alt: prefetch performance - -Other features --------------- - -Parallelism -^^^^^^^^^^^ - -CPython and many other implementations alike cannot take advantage of parallelism due to the infamous global interpreter lock, a mutex that protects accesses to Python objects, preventing multiple threads from executing Python bytecode at once. Unlike CPython, Seq has no such restriction and supports full multithreading. To this end, Seq supports a *parallel* pipe operator ``||>``, which is semantically similar to the standard pipe operator except that it allows the elements sent through it to be processed in parallel by the remainder of the pipeline. Hence, turning a serial program into a parallel one often requires the addition of just a single character in Seq. Further, a single pipeline can contain multiple parallel pipes, resulting in nested parallelism. As an example, here are the same two pipelines as above, but parallelized: - -.. code-block:: seq - - dna = s'ACGTACGTACGT' # sequence literal - - # (a) split into subsequences of length 3 - # with a stride of 2 - dna |> split(..., k=3, step=2) ||> print - - # (b) split into 5-mers with stride 1 - def f(kmer): - print(kmer) - print(~kmer) - - dna |> kmers(k=5, step=1) ||> f - -Internally, the Seq compiler uses an OpenMP task backend to generate code for parallel pipelines. Logically, parallel pipe operators are similar to parallel-for loops: the portion of the pipeline after the parallel pipe is outlined into a new function that is called by the OpenMP runtime task spawning routines (as in ``#pragma omp task`` in C++), and a synchronization point (``#pragma omp taskwait``) is added after the outlined segment. Lastly, the entire program is implicitly placed in an OpenMP parallel region (``#pragma omp parallel``) that is guarded by a "single" directive (``#pragma omp single``) so that the serial portions are still executed by one thread (this is required by OpenMP as tasks must be bound to an enclosing parallel region). - -Type extensions -^^^^^^^^^^^^^^^ - -Seq provides an ``@extend`` annotation that allows programmers to add and modify methods of various types at compile time, including built-in types like ``int`` or ``str``. This actually allows much of the functionality of built-in types to be implemented in Seq as type extensions in the standard library. Here is an example where the ``int`` type is extended to include a ``to`` method that generates integers in a specified range, as well as to override the ``__mul__`` magic method to "intercept" integer multiplications: - -.. code-block:: seq - - @extend - class int: - def to(self, other: int): - for i in range(self, other + 1): - yield i - - def __truediv__(self, other: int): - print('caught int div!') - return 42 - - for i in (5).to(10): - print(i) # 5, 6, ..., 10 - - # prints 'caught int div!' then '42' - print(2 / 3) - -Note that all type extensions are performed strictly at compile time and incur no runtime overhead. - -Other types -^^^^^^^^^^^ - -Seq provides arbitrary-width signed and unsigned integers up to ``Int[512]`` and ``UInt[512]``, respectively (note that ``int`` is an ``Int[64]``). Typedefs for common bit widths are provided in the standard library, such as ``i8``, ``i16``, ``u32``, ``u64`` etc. - -The ``Ptr[T]`` type in Seq also corresponds to a raw C pointer (e.g. ``Ptr[byte]`` is equivalent to ``char*`` in C). The ``array[T]`` type represents a fixed-length array (essentially a pointer with a length). - -Seq also provides ``__ptr__`` for obtaining a pointer to a variable (as in ``__ptr__(myvar)``) and ``__array__`` for declaring stack-allocated arrays (as in ``__array__[int](10)``). - -Calling BWA from Seq --------------------- - -Seq provides a built-in module for interfacing with BWA. To use this module, simply build a shared BWA library and set ``BWA_LIB`` accordingly: - -.. code-block:: bash - - git clone https://github.com/lh3/bwa - cd bwa - make - gcc -shared -o libbwa.so *.o -lz - export BWA_LIB=`pwd`/libbwa.so - -Now BWA can be used in Seq as such: - -.. code-block:: seq - - # Implementation of https://github.com/lh3/bwa/blob/master/example.c - from sys import argv - from bio.bwa import * - - bwa = BWA(argv[1]) - for read in FASTQ(argv[2]): - for reg in bwa.align(read.read): - if reg.secondary >= 0: continue - aln = bwa.reg2aln(read.read, reg) - print(read.name, '-' if aln.rev else '+', bwa.name(aln), aln.pos, aln.mapq, aln.cigar, aln.NM) - -This program can be invoked as ``seqc run example.seq /path/to/hg19.fa /path/to/reads.fq``. - -BWA options can be passed via ``BWA(options(...), ...)``. For example, to set a mismatch score of 5, use ``BWA(options(mismatch_score=5), "hg19.fa")``. Valid options are: - -- ``match_score`` -- ``mismatch_score`` -- ``open_del`` -- ``open_ins`` -- ``extend_del`` -- ``extend_ins`` -- ``bandwidth`` -- ``zdrop`` -- ``clip_penalty`` -- ``unpaired_penalty`` - -Consult the BWA documentation for a detailed description of each of these. diff --git a/docs/sphinx/tutorial/workshop.rst b/docs/sphinx/tutorial/workshop.rst deleted file mode 100644 index e39c8ffb..00000000 --- a/docs/sphinx/tutorial/workshop.rst +++ /dev/null @@ -1,770 +0,0 @@ -Workshop -======== - -In this workshop, we will build a toy read mapper called *SeqMap* to -showcase some of Seq's domain-specific features and optimizations. - -Code Listings -------------- - -- **Section 1**: :ref:`section1-code` | :download:`click to download <../../workshop/section1.seq>` -- **Section 2**: :ref:`section2-code` | :download:`click to download <../../workshop/section2.seq>` -- **Section 3**: :ref:`section3-code` | :download:`click to download <../../workshop/section3.seq>` -- **Section 4**: :ref:`section4-code` | :download:`click to download <../../workshop/section4.seq>` -- **Section 5**: :ref:`section5-code` | :download:`click to download <../../workshop/section5.seq>` -- **Section 6**: :ref:`section6-code` | :download:`click to download <../../workshop/section6.seq>` - -Getting Started ---------------- - -If you don't have Seq installed already, you can install it with one bash command: - -.. code:: bash - - /bin/bash -c "$(curl -fsSL https://seq-lang.org/install.sh)" - -Be sure to restart the shell for ``seqc`` to be added to your ``PATH`` (or add it manually). - -Now, let's create a new directory to house our Seq code and test data: - -.. code:: bash - - mkdir seqmap - cd seqmap - -We'll test *SeqMap* on the following data: - -- Chromosome 22 as the reference sequence (``chr22.fa``, 52MB) -- A simulated set of 1 million 101bp reads (``reads.fastq``, 251MB) - -Let's download this data into a new folder called ``data``: - -.. code:: bash - - curl -L https://www.dropbox.com/s/8lsngqvn0tzjn1o/data.tar.gz | tar zxf - -C . - -What does this data actually look like? Let's take a look: - -.. code:: bash - - head data/reads.fq - -.. code:: text - - @chr22_16993648_16994131_1:0:0_2:0:0_0/1 - CTACCAAACACCTACTTCGTTTCCTAACATCACTTTAATTTTATCTTAGAGGAATTCTTTTCCCTATCCCATTAAGTTATGGGAGATGGGGCCAGGCATGG - + - 55555555555555555555555555555555555555555555555555555555555555555555555555555555555555555555555555555 - @chr22_28253010_28253558_1:0:0_0:0:0_1/1 - AGTGTTTTGCCTGTGGCTAGACTAAAAATAAGGAATGAGGGGGGTATCTTCCACTCTTGCCCTCTCATCACCCTATTCCCTATATCCAGAACTCAGAGTCC - + - 55555555555555555555555555555555555555555555555555555555555555555555555555555555555555555555555555555 - @chr22_21656192_21656802_0:0:0_2:0:0_2/1 - ATAGCGTGGATTCCTATGACATCAAGGAGCTATTTTATTTGGTAAAACGAAAAAGCACAATAATGAACGAACGCAAGCACTGAAACAGTGGAGACACCTAG - -Each `FASTQ `_ record consists of four lines: - -- Read name, starting with ``@``. Notice that since this data is simulated, the read name includes the - location on the genome where the read comes from; this will be useful later! -- Read sequence. This is a DNA sequence consisting of ``ACGT`` bases and possibly ``N``, indicating an - ambiguous base. -- Separator (``+``) -- Read quality scores. This is a string of characters as long as the read sequence, where each character - indicates the "quality" of the corresponding base in the read sequence. We won't be using it here. - -What about the reference sequence `FASTA `_ file? - -.. code:: bash - - head data/chr22.fa - -.. code:: text - - >chr22 - NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN - NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN - NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN - NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN - NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN - NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN - NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN - NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN - NNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNNN - -FASTQ records start with the sequence name (prefixed with ``>``) followed by the sequence itself, split -across multiple lines. But why are all the bases ``N``? Chromosomal sequences often have their starts -and ends masked with ``N``'s to cover repetitive `telomeric `_ sequences. -Since we usually don't want to include such regions in our analyses, they are masked in the file. Let's -look a bit further down: - -.. code:: bash - - head -n 1000000 data/chr22.fa | tail -n 10 - -.. code:: text - - tattaaaggaaaaaactgtatgaaatagtacatttctcataattctcatt - ttgtaaaaataaagtacttatctatggacataatgagaaaatgactcaag - gtaccaagagtttagccattagctataccagtggattataagcaaattct - gttACGTGCATGCACTCACCTACGCATGTTCATGTATTCATACATACGTA - CATAATTTTTTAAATTTTCTTTTATAGACAAGCAATAGCTTTATAATCTC - TATAATCAGTAAAAATAAGTAAGTggctggacgcagtggctcacacctgt - aatctcagcactttgggaggctgaggagggcagattatgaggtcagaaga - tcaagaccatcctggctaacacagtgaaaccccatctctactaaaaatac - aaaaaattagccacgcgtggtggcacgcgcctgtagtcccagctactggg - gaggctgaggcaggaaaatcgcttgaacccgggaggcagaggttgcggtg - -Now we can see the usual ``ACGT`` bases. The fact that some bases are lowercase indicates that they -are a part of some repetitive element or region. Seq will handle these different uppercase and lowercase -characters automatically, so we don't need to worry about them. - -You might notice an additional file called ``chr22.fa.fai``: this is a FASTA index file that includes -information about each sequence contained in the file for easier parsing. We won't use it directly, -but Seq uses it internally to make FASTA parsing more efficient. - - -Section 1: Reading sequences from disk --------------------------------------- - -The first step of processing any kind of sequencing data is to read it from disk. -Seq has builtin support for many of the standard file formats such as FASTA, FASTQ, -SAM, BAM, etc. - -Let's write a program to read our FASTQ file and print each record's name and sequence -on a single line: - -.. code:: seq - - from sys import argv - from bio import * - for record in FASTQ(argv[1]): - print(record.name, record.seq) - -Now we can run this Seq program: - -.. code:: bash - - seqc run section1.seq data/reads.fq > out.txt - -and view the results: - -.. code:: bash - - head out.txt - -.. code:: text - - chr22_16993648_16994131_1:0:0_2:0:0_0/1 CTACCAAACACCTACTTCGTTTCCTAACATCACTTTAATTTTATCTTAGAGGAATTCTTTTCCCTATCCCATTAAGTTATGGGAGATGGGGCCAGGCATGG - chr22_28253010_28253558_1:0:0_0:0:0_1/1 AGTGTTTTGCCTGTGGCTAGACTAAAAATAAGGAATGAGGGGGGTATCTTCCACTCTTGCCCTCTCATCACCCTATTCCCTATATCCAGAACTCAGAGTCC - chr22_21656192_21656802_0:0:0_2:0:0_2/1 ATAGCGTGGATTCCTATGACATCAAGGAGCTATTTTATTTGGTAAAACGAAAAAGCACAATAATGAACGAACGCAAGCACTGAAACAGTGGAGACACCTAG - chr22_44541236_44541725_0:1:0_0:0:0_3/1 CTCTCTGTCTCTCTCTCTCCCCTAGGTCAGGGTGGTCCCTGGGGAGGCCCCTGGGTTACCCCAAGACAGGTGGGAGGTGCTTCCTACCCGACCCTCTTCCT - chr22_39607671_39608139_0:0:0_2:0:0_4/1 ATTGGCTCAGAGTTCAGCAGGCTGTACCAGCATGGCGCCAGTGTCTGCTCCTGGTGAGGCCTTACGGACGTTACAATAACGGCGGAAGGCAAAGGCGGAGC - chr22_35577703_35578255_3:0:0_1:0:0_5/1 TGCCATGGTGGTTAGCTGCACCCATCAACCTGTCATCTACATTAGGTATTTTTCCTAATGCTATCCCTCCCCTAGCACCCTACCCTCTGATAGGCCCTGGT - chr22_46059124_46059578_1:0:0_1:0:0_6/1 AATCAGTACCAAACAATATATGGATATTATTGGCACTTTGTGCTCCCTCTGCCTGAACTGGGAATTCCTCTATTAGTTTTGACATTATCTGGTATTGAACC - chr22_31651867_31652385_2:0:0_2:0:0_7/1 ATCTAGTGACAGTAAGTGGCTGATAAAGTGAGCTGCCATTACATAGTCATCATCTTTAATAGAAGTTAACACATACTGAGTTTCTACTATATTGGGTCTTT - chr22_24816466_24817026_1:0:0_1:0:0_8/1 CACCTCTAGGGCTCAAGGGGCAGTTCCTCCATTCCTCAGCAGTGGCGCCTGTGGAACTGTGTCCTGAGGCCAGGGGGTGGTCAGGCAGGGCCTGGAGTGGC - chr22_27496272_27496752_1:0:0_1:0:0_9/1 CTTAGCCCCATTAAACACTGGCAGGGCTGAATTGTCTGCTGCCATCCATCACACCTTCTCCCCTAGCCTGGTTTCTTACCTACCTGGAAGCCGTCCCTTTT - -Pretty straightforward! FASTA files can be read in a very similar way. - -.. _section1-code: - -Full code listing -~~~~~~~~~~~~~~~~~ - -:download:`click to download <../../workshop/section1.seq>` - -.. code:: seq - - # SeqMap - # Seq workshop -- Section 1 - # Reads and prints a FASTQ file. - # Usage: seqc run section1.seq - from sys import argv - from bio import * - for record in FASTQ(argv[1]): - print(record.name, record.seq) - - -Section 2: Building an index ----------------------------- - -Our goal is to find a "mapping" on the genome for each read. Comparing to every -position on the reference sequence would take far too long. An alternative is -to create an index of the k-mers from the reference sequence and use it to guide -the mapping process. - -Let's build a dictionary that maps each k-mer to its position ("locus") on the -reference sequence: - -.. code:: seq - - from sys import argv - from bio import * - index = {} - - for record in FASTA(argv[1]): - for pos,kmer in record.seq.kmers_with_pos(k=32, step=1): - index[kmer] = pos - -Of course, there will be k-mers that appear multiple times, but let's ignore this -detail for now and just store the latest position we see for each k-mer. - -Another important issue is *reverse complementation*: some of our reads will map -in the reverse direction rather than in the forward direction. For this reason, -let's build our index in such a way that a k-mer is considered "equal" to its -reverse complement. One easy way to do this is by using "canonical" k-mers, i.e. -the minimum of a k-mer and its reverse complement: - -.. code:: seq - - from sys import argv - from bio import * - index = {} - - for record in FASTA(argv[1]): - for pos,kmer in record.seq.kmers_with_pos(k=32, step=1): - index[min(kmer, ~kmer)] = pos # <-- - -(We'll have to use canonical k-mers when querying the index too, of course.) - -Now we have our index as a dictionary (``index``), but we don't want to build it -each time we perform read mapping, since it only depends on the (fixed) reference -sequence. So, as a last step, let's dump the index to a file using the ``pickle`` -module: - -.. code:: seq - - import pickle - import gzip - - with gzip.open(argv[1] + '.index', 'wb') as jar: - pickle.dump(index, jar) - -Run the program: - -.. code:: bash - - seqc run section2.seq data/chr22.fa - -Now we should see a new file ``data/chr22.fa.index`` which stores our -serialized index. - -The nice thing is we should only have to build our index once! - -.. _section2-code: - -Full code listing -~~~~~~~~~~~~~~~~~ - -:download:`click to download <../../workshop/section2.seq>` - -.. code:: seq - - # SeqMap - # Seq workshop -- Section 2 - # Reads and constructs a hash table index from an input - # FASTA file. - # Usage: seqc run section2.seq - from sys import argv - from bio import * - import pickle - import gzip - - index = {} - - for record in FASTA(argv[1]): - for pos,kmer in record.seq.kmers_with_pos(k=32, step=1): - index[min(kmer, ~kmer)] = pos - - with gzip.open(argv[1] + '.index', 'wb') as jar: - pickle.dump(index, jar) - - -Section 3: Finding k-mer matches --------------------------------- - -At this point, we have an index we can load from disk. Let's use it -to find candidate mappings for our reads. - -We'll split each read into k-mers and report a mapping if at least two -k-mers support a particular locus. - -The first step is to load the index: - -.. code:: seq - - from sys import argv - from bio import * - import pickle - import gzip - - K: Static[int] = 32 - index = None - - with gzip.open(argv[1] + '.index', 'rb') as jar: - index = pickle.load(jar, T=Dict[Kmer[K],int]) - -Now we can iterate over our reads and query k-mers in the index. We need -a way to keep track of candidate mapping positions as we process the -k-mers of a read: we can do this using a new dictionary, ``candidates``, -which maps candidate alignment positions to the number of k-mers supporting -the given position. - -Then, we just iterate over ``candidates`` and output positions supported by -2 or more k-mers. Finally, we clear ``candidates`` before processing the next -read: - -.. code:: seq - - candidates = {} # position -> count mapping - for record in FASTQ(argv[2]): - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - - for pos,count in candidates.items(): - if count > 1: - print(record.name, pos + 1) - - candidates.clear() - -Run the program: - -.. code:: bash - - seqc run section3.seq data/chr22.fa data/reads.fq > out.txt - -Let's take a look at the output: - -.. code:: bash - - head out.txt - -.. code:: text - - chr22_16993648_16994131_1:0:0_2:0:0_0/1 16993648 - chr22_28253010_28253558_1:0:0_0:0:0_1/1 28253010 - chr22_44541236_44541725_0:1:0_0:0:0_3/1 44541236 - chr22_31651867_31652385_2:0:0_2:0:0_7/1 31651867 - chr22_21584577_21585142_1:0:0_1:0:0_a/1 21584577 - chr22_46629499_46629977_0:0:0_2:0:0_b/1 47088563 - chr22_46629499_46629977_0:0:0_2:0:0_b/1 51103174 - chr22_46629499_46629977_0:0:0_2:0:0_b/1 46795988 - chr22_16269615_16270134_0:0:0_1:0:0_c/1 50577316 - chr22_16269615_16270134_0:0:0_1:0:0_c/1 16269615 - -Notice that most positions we reported match the position from the read -name (the first integer after the ``_``); not bad! - -.. _section3-code: - -Full code listing -~~~~~~~~~~~~~~~~~ - -:download:`click to download <../../workshop/section3.seq>` - -.. code:: seq - - # SeqMap - # Seq workshop -- Section 3 - # Reads index constructed in Section 2 and looks up k-mers from - # input reads to find candidate mappings. - # Usage: seqc run section3.seq - from sys import argv - from bio import * - import pickle - import gzip - - K: Static[int] = 32 - index = None - - with gzip.open(argv[1] + '.index', 'rb') as jar: - index = pickle.load(jar, T=Dict[Kmer[K],int]) - - candidates = {} # position -> count mapping - for record in FASTQ(argv[2]): - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - - for pos,count in candidates.items(): - if count > 1: - print(record.name, pos + 1) - - candidates.clear() - - -Section 4: Smith-Waterman alignment and CIGAR strings ------------------------------------------------------ - -We now have the ability to report mapping *positions* for each read, -but usually we want *alignments*, which include information about -mismatches, insertions and deletions. - -Luckily, Seq makes sequence alignment easy: to align sequence ``q`` -against sequence ``t``, you can just do: - -.. code:: seq - - aln = q @ t - -``aln`` is a tuple of alignment score and CIGAR string (a *CIGAR string* is -a way of encoding an alignment result, and consists of operations such as ``M`` -for match/mismatch, ``I`` for insertion and ``D`` for deletion, accompanied -by the number of associated bases; for example, ``3M2I4M`` indicates 3 (mis)matches -followed by a length-2 insertion followed by 4 (mis)matches). - -By default, `Levenshtein distance `_ is -used, meaning mismatch and gap costs are both 1, while match costs are zero. More -control over alignment parameters can be achieved using the ``align`` method: - -.. code:: seq - - aln = q.align(t, a=2, b=4, ambig=0, gapo=4, gape=2) - -where ``a`` is the match score, ``b`` is the mismatch cost, ``ambig`` is the -ambiguous base (``N``) match score, ``gapo`` is the gap open cost and ``gape`` -the gap extension cost (i.e. a gap of length ``k`` costs ``gapo + (k * gape)``). -There are many more parameters as well, controlling factors like alignment bandwidth, -Z-drop, global/extension alignment and more; check the -`standard library reference `_ -for further details. - -For now, we'll use a simple ``query.align(target)``: - -.. code:: seq - - candidates = {} # position -> count mapping - for record in FASTQ(argv[2]): - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - - for pos,count in candidates.items(): - if count > 1: - # get query, target and align: - query = record.read - target = reference[pos:pos + len(query)] - alignment = query.align(target) - print(record.name, pos + 1, alignment.score, alignment.cigar) - - candidates.clear() - -Run the program: - -.. code:: bash - - seqc run section4.seq data/chr22.fa data/reads.fq > out.txt - -And let's take a look at the output once again: - -.. code:: bash - - head out.txt - -.. code:: text - - chr22_16993648_16994131_1:0:0_2:0:0_0/1 16993648 196 101M - chr22_28253010_28253558_1:0:0_0:0:0_1/1 28253010 196 101M - chr22_44541236_44541725_0:1:0_0:0:0_3/1 44541236 196 101M - chr22_31651867_31652385_2:0:0_2:0:0_7/1 31651867 190 101M - chr22_21584577_21585142_1:0:0_1:0:0_a/1 21584577 196 101M - chr22_46629499_46629977_0:0:0_2:0:0_b/1 47088563 110 20M1I4M1D76M - chr22_46629499_46629977_0:0:0_2:0:0_b/1 51103174 134 20M1I4M1D76M - chr22_46629499_46629977_0:0:0_2:0:0_b/1 46795988 128 20M1I4M1D76M - chr22_16269615_16270134_0:0:0_1:0:0_c/1 50577316 118 101M - chr22_16269615_16270134_0:0:0_1:0:0_c/1 16269615 202 101M - -Most of the alignments contain only matches or mismatches (``M``), which -is to be expected as insertions and deletions are far less common. In fact, -the three mappings containing indels appear to be incorrect! - -A more thorough mapping scheme would also look at alignment scores before -reporting mappings, although for the purposes of this workshop we'll ignore -such improvements. - -.. _section4-code: - -Full code listing -~~~~~~~~~~~~~~~~~ - -:download:`click to download <../../workshop/section4.seq>` - -.. code:: seq - - # SeqMap - # Seq workshop -- Section 4 - # Reads index constructed in Section 2 and looks up k-mers from - # input reads to find candidate mappings, then performs alignment. - # Usage: seqc run section4.seq - from sys import argv - from bio import * - import pickle - import gzip - - reference = s'' - for record in FASTA(argv[1]): - reference = record.seq - - K: Static[int] = 32 - index = None - - with gzip.open(argv[1] + '.index', 'rb') as jar: - index = pickle.load(jar, T=Dict[Kmer[K],int]) - - candidates = {} # position -> count mapping - for record in FASTQ(argv[2]): - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - - for pos,count in candidates.items(): - if count > 1: - query = record.read - target = reference[pos:pos + len(query)] - alignment = query.align(target) - print(record.name, pos + 1, alignment.score, alignment.cigar) - - candidates.clear() - - -Section 5: Pipelines --------------------- - -Pipelines are a very convenient Seq construct for expressing a variety -of algorithms and applications. In fact, *SeqMap* can be thought of as -a pipeline with the following stages: - -- read a record from the FASTQ file, -- find candidate alignments by querying the index, -- perform alignment for mappings supported by 2+ k-mers and output results. - -We can write this as a pipeline in Seq as follows: - -.. code:: seq - - def find_candidates(record): - candidates = {} # position -> count mapping - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - for pos,count in candidates.items(): - if count > 1: - yield record, pos - - def align_and_output(t): - record, pos = t - query = record.read - target = reference[pos:pos + len(query)] - alignment = query.align(target) - print(record.name, pos + 1, alignment.score, alignment.cigar) - -Notice that ``find_candidates`` *yields* candidate alignments to ``align_and_output``, -which then performs alignment and prints the results. In Seq, all values generated -from one stage of a pipeline are passed to the next. The Seq compiler performs many -domain-specific optimizations on pipelines, one of which we focus on in the next section. - -(Optional) Parallelism -~~~~~~~~~~~~~~~~~~~~~~ - -Parallelism can be achieved using the parallel pipe operator, ``||>``, which -tells the compiler that all subsequent stages can be executed in parallel: - -.. code:: seq - - FASTQ(argv[2]) |> iter ||> find_candidates |> align_and_output - -Since the full program also involves loading the index, let's time the main -pipeline using the ``timing`` module: - -.. code:: seq - - import timing - with timing('mapping'): - FASTQ(argv[2]) |> iter ||> find_candidates |> align_and_output - -We can try this for different numbers of threads: - -.. code:: bash - - export OMP_NUM_THREADS=1 - seqc run section5.seq data/chr22.fa data/reads.fq > out.txt - # mapping took 48.2858s - - export OMP_NUM_THREADS=2 - seqc run section5.seq data/chr22.fa data/reads.fq > out.txt - # mapping took 35.886s - -Often, batching reads into larger blocks and processing those blocks in parallel can -yield better performance, especially if each read is quick to process. This is also -very easy to do in Seq: - -.. code:: seq - - def process_block(block): - block |> iter |> find_candidates |> align_and_output - - with timing('mapping'): - FASTQ(argv[2]) |> blocks(size=2000) ||> process_block - -And now: - -.. code:: bash - - export OMP_NUM_THREADS=1 - seqc run section5.seq data/chr22.fa data/reads.fq > out.txt - # mapping took 48.2858s - - export OMP_NUM_THREADS=2 - seqc run section5.seq data/chr22.fa data/reads.fq > out.txt - # mapping took 25.2648s - -.. _section5-code: - -Full code listing -~~~~~~~~~~~~~~~~~ - -:download:`click to download <../../workshop/section5.seq>` - -.. code:: seq - - # SeqMap - # Seq workshop -- Section 5 - # Reads index constructed in Section 2 and looks up k-mers from - # input reads to find candidate mappings, then performs alignment. - # Implemented with Seq pipelines. - # Usage: seqc run section5.seq - from sys import argv - from time import timing - from bio import * - import pickle - import gzip - - reference = s'' - for record in FASTA(argv[1]): - reference = record.seq - - K: Static[int] = 32 - index = None - - with gzip.open(argv[1] + '.index', 'rb') as jar: - index = pickle.load(jar, T=Dict[Kmer[K],int]) - - def find_candidates(record): - candidates = {} # position -> count mapping - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - for pos,count in candidates.items(): - if count > 1: - yield record, pos - - def align_and_output(t): - record, pos = t - query = record.read - target = reference[pos:pos + len(query)] - alignment = query.align(target) - print(record.name, pos + 1, alignment.score, alignment.cigar) - - with timing('mapping'): - FASTQ(argv[2]) |> iter |> find_candidates |> align_and_output - - -Section 6: Domain-specific optimizations ----------------------------------------- - -Seq already performs numerous domain-specific optimizations under the hood. -However, we can give the compiler a hint in this case to perform one more: -*inter-sequence alignment*. This optimization entails batching sequences -prior to alignment, then aligning multiple pairs using a very fast SIMD -optimized alignment kernel. - -In Seq, we just need one additional function annotation to tell the compiler -to perform this optimization: - -.. code:: seq - - @inter_align - def align_and_output(t): - ... - -Let's run the program with and without this optimization: - -.. code:: seq - - # without @inter_align - seqc run section5.seq data/chr22.fa data/reads.fq > out.txt - # mapping took 43.4457s - - # with @inter_align - seqc run section6.seq data/chr22.fa data/reads.fq > out.txt - # mapping took 32.3241s - -(The timings with inter-sequence alignment will depend on the SIMD instruction -sets your CPU supports; these numbers are from using AVX2.) - -.. _section6-code: - -Full code listing -~~~~~~~~~~~~~~~~~ - -:download:`click to download <../../workshop/section6.seq>` - -.. code:: seq - - # SeqMap - # Seq workshop -- Section 6 - # Reads index constructed in Section 2 and looks up k-mers from - # input reads to find candidate mappings, then performs alignment. - # Implemented with Seq pipelines using inter-seq. alignment. - # Usage: seqc run section6.seq - from sys import argv - from time import timing - from bio import * - import pickle - import gzip - - reference = s'' - for record in FASTA(argv[1]): - reference = record.seq - - K: Static[int] = 32 - index = None - - with gzip.open(argv[1] + '.index', 'rb') as jar: - index = pickle.load(jar, T=Dict[Kmer[K],int]) - - def find_candidates(record): - candidates = {} # position -> count mapping - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - for pos,count in candidates.items(): - if count > 1: - yield record, pos - - @inter_align - def align_and_output(t): - record, pos = t - query = record.read - target = reference[pos:pos + len(query)] - alignment = query.align(target) - print(record.name, pos + 1, alignment.score, alignment.cigar) - - with timing('mapping'): - FASTQ(argv[2]) |> iter |> find_candidates |> align_and_output diff --git a/docs/workshop/section1.codon b/docs/workshop/section1.codon deleted file mode 100644 index 82092a7b..00000000 --- a/docs/workshop/section1.codon +++ /dev/null @@ -1,8 +0,0 @@ -# SeqMap -# Seq workshop -- Section 1 -# Reads and prints a FASTQ file. -# Usage: seqc run section1.seq -from sys import argv -from bio import * -for record in FASTQ(argv[1]): - print(record.name, record.seq) diff --git a/docs/workshop/section2.codon b/docs/workshop/section2.codon deleted file mode 100644 index f05b41a8..00000000 --- a/docs/workshop/section2.codon +++ /dev/null @@ -1,18 +0,0 @@ -# SeqMap -# Seq workshop -- Section 2 -# Reads and constructs a hash table index from an input -# FASTA file. -# Usage: seqc run section2.seq -from sys import argv -from bio import * -import pickle -import gzip - -index = {} - -for record in FASTA(argv[1]): - for pos,kmer in record.seq.kmers_with_pos(k=32, step=1): - index[min(kmer, ~kmer)] = pos - -with gzip.open(argv[1] + '.index', 'wb') as jar: - pickle.dump(index, jar) diff --git a/docs/workshop/section3.codon b/docs/workshop/section3.codon deleted file mode 100644 index ed12d95b..00000000 --- a/docs/workshop/section3.codon +++ /dev/null @@ -1,29 +0,0 @@ -# SeqMap -# Seq workshop -- Section 3 -# Reads index constructed in Section 2 and looks up k-mers from -# input reads to find candidate mappings. -# Usage: seqc run section3.seq -from sys import argv -from bio import * -import pickle -import gzip - -K: Static[int] = 32 -index = None - -with gzip.open(argv[1] + '.index', 'rb') as jar: - index = pickle.load(jar, T=Dict[Kmer[K],int]) - -candidates = {} # position -> count mapping -for record in FASTQ(argv[2]): - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - - for pos,count in candidates.items(): - if count > 1: - print(record.name, pos + 1) - - candidates.clear() diff --git a/docs/workshop/section4.codon b/docs/workshop/section4.codon deleted file mode 100644 index 11f8c80a..00000000 --- a/docs/workshop/section4.codon +++ /dev/null @@ -1,36 +0,0 @@ -# SeqMap -# Seq workshop -- Section 4 -# Reads index constructed in Section 2 and looks up k-mers from -# input reads to find candidate mappings, then performs alignment. -# Usage: seqc run section4.seq -from sys import argv -from bio import * -import pickle -import gzip - -reference = s'' -for record in FASTA(argv[1]): - reference = record.seq - -K: Static[int] = 32 -index = None - -with gzip.open(argv[1] + '.index', 'rb') as jar: - index = pickle.load(jar, T=Dict[Kmer[K],int]) - -candidates = {} # position -> count mapping -for record in FASTQ(argv[2]): - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - - for pos,count in candidates.items(): - if count > 1: - query = record.read - target = reference[pos:pos + len(query)] - alignment = query.align(target) - print(record.name, pos + 1, alignment.score, alignment.cigar) - - candidates.clear() diff --git a/docs/workshop/section5.codon b/docs/workshop/section5.codon deleted file mode 100644 index 7322db1a..00000000 --- a/docs/workshop/section5.codon +++ /dev/null @@ -1,42 +0,0 @@ -# SeqMap -# Seq workshop -- Section 5 -# Reads index constructed in Section 2 and looks up k-mers from -# input reads to find candidate mappings, then performs alignment. -# Implemented with Seq pipelines. -# Usage: seqc run section5.seq -from sys import argv -from time import timing -from bio import * -import pickle -import gzip - -reference = s'' -for record in FASTA(argv[1]): - reference = record.seq - -K: Static[int] = 32 -index = None - -with gzip.open(argv[1] + '.index', 'rb') as jar: - index = pickle.load(jar, T=Dict[Kmer[K],int]) - -def find_candidates(record): - candidates = {} # position -> count mapping - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - for pos,count in candidates.items(): - if count > 1: - yield record, pos - -def align_and_output(t): - record, pos = t - query = record.read - target = reference[pos:pos + len(query)] - alignment = query.align(target) - print(record.name, pos + 1, alignment.score, alignment.cigar) - -with timing('mapping'): - FASTQ(argv[2]) |> iter |> find_candidates |> align_and_output diff --git a/docs/workshop/section6.codon b/docs/workshop/section6.codon deleted file mode 100644 index 5f662fea..00000000 --- a/docs/workshop/section6.codon +++ /dev/null @@ -1,43 +0,0 @@ -# SeqMap -# Seq workshop -- Section 6 -# Reads index constructed in Section 2 and looks up k-mers from -# input reads to find candidate mappings, then performs alignment. -# Implemented with Seq pipelines using inter-seq. alignment. -# Usage: seqc run section6.seq -from sys import argv -from time import timing -from bio import * -import pickle -import gzip - -reference = s'' -for record in FASTA(argv[1]): - reference = record.seq - -K: Static[int] = 32 -index = None - -with gzip.open(argv[1] + '.index', 'rb') as jar: - index = pickle.load(jar, T=Dict[Kmer[K],int]) - -def find_candidates(record): - candidates = {} # position -> count mapping - for pos,kmer in record.read.kmers_with_pos(k=K, step=1): - found = index.get(min(kmer, ~kmer), -1) - if found > 0: - loc = found - pos - candidates[loc] = candidates.get(loc, 0) + 1 - for pos,count in candidates.items(): - if count > 1: - yield record, pos - -@inter_align -def align_and_output(t): - record, pos = t - query = record.read - target = reference[pos:pos + len(query)] - alignment = query.align(target) - print(record.name, pos + 1, alignment.score, alignment.cigar) - -with timing('mapping'): - FASTQ(argv[2]) |> iter |> find_candidates |> align_and_output diff --git a/stdlib/time.codon b/stdlib/time.codon index de1e575c..4a64c976 100644 --- a/stdlib/time.codon +++ b/stdlib/time.codon @@ -37,7 +37,7 @@ def timing(msg: str = ""): """ Example usage: - .. code-block:: seq + .. code-block:: python from time import timing with timing('foo function'):