Skip to content

Commit

Permalink
Include docs
Browse files Browse the repository at this point in the history
  • Loading branch information
greshilov committed Nov 14, 2021
1 parent 87df11a commit c6d3f99
Show file tree
Hide file tree
Showing 10 changed files with 325 additions and 5 deletions.
15 changes: 15 additions & 0 deletions .github/workflows/ci.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -22,11 +22,26 @@ jobs:
uses: actions/setup-python@v2
with:
python-version: 3.9
- name: Cache PyPI
uses: actions/cache@v2.1.6
with:
key: pip-lint-${{ hashFiles('requirements.dev.txt') }}
path: ~/.cache/pip
restore-keys: |
pip-lint-
- name: Install dependencies
uses: py-actions/py-dependency-install@v2
with:
path: requirements.dev.txt
- name: Pre-Commit hooks
uses: pre-commit/action@v2.0.3
- name: Build docs
run:
make doc

test:
name: Test
needs: lint
strategy:
matrix:
pyver: ['3.8', '3.9', '3.10']
Expand Down
4 changes: 4 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,10 @@ compile-deps: .update-pip
pip-compile --allow-unsafe -q --strip-extras \
requirements.dev.in

.PHONY: doc
doc: .develop
@make -C docs html SPHINXOPTS="-W -E"

.PHONY: fmt format
fmt format:
python -m pre_commit run --all-files --show-diff-on-failure
Expand Down
5 changes: 4 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
[![CI](https://github.com/greshilov/pysegmenttree/actions/workflows/ci.yaml/badge.svg)](https://github.com/greshilov/pysegmenttree/actions/workflows/ci.yaml)
[![codecov](https://codecov.io/gh/greshilov/pysegmenttree/branch/master/graph/badge.svg?token=BXXCG2JBPK)](https://codecov.io/gh/greshilov/pysegmenttree)

Segment tree is a data structure to store information about intervals and perform efficient queries on them.
Segment tree is a data structure to perform efficient range queries over an array.

Properties of the segment tree with the size N.

Expand Down Expand Up @@ -39,6 +39,9 @@ $ pip install pysegmenttree
16
```

# Docs
Docs are available [here](https://pysegmenttree.readthedocs.io/en/latest/).

# Development

## Insall dependencies
Expand Down
20 changes: 20 additions & 0 deletions docs/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
# Minimal makefile for Sphinx documentation
#

# You can set these variables from the command line, and also
# from the environment for the first two.
SPHINXOPTS ?=
SPHINXBUILD ?= sphinx-build
SOURCEDIR = .
BUILDDIR = _build

# Put it first so that "make" without argument is like "make help".
help:
@$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O)

.PHONY: help Makefile

# Catch-all target: route all unknown targets to Sphinx using the new
# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS).
%: Makefile
@$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O)
55 changes: 55 additions & 0 deletions docs/conf.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
# Configuration file for the Sphinx documentation builder.
#
# This file only contains a selection of the most common options. For a full
# list see the documentation:
# https://www.sphinx-doc.org/en/master/usage/configuration.html

# -- Path setup --------------------------------------------------------------

# If extensions (or modules to document with autodoc) are in another directory,
# add these directories to sys.path here. If the directory is relative to the
# documentation root, use os.path.abspath to make it absolute, like shown here.
#
# import os
# import sys
# sys.path.insert(0, os.path.abspath('.'))


# -- Project information -----------------------------------------------------

project = "pysegmenttree"
copyright = "2021, Viacheslav Greshilov"
author = "Viacheslav Greshilov"


# -- General configuration ---------------------------------------------------

# Add any Sphinx extension module names here, as strings. They can be
# extensions coming with Sphinx (named 'sphinx.ext.*') or your custom
# ones.
extensions = [
"sphinx.ext.autodoc",
"sphinx.ext.extlinks",
"sphinx.ext.viewcode",
]

# Add any paths that contain templates here, relative to this directory.
templates_path = []

# List of patterns, relative to source directory, that match files and
# directories to ignore when looking for source files.
# This pattern also affects html_static_path and html_extra_path.
exclude_patterns = ["_build", "Thumbs.db", ".DS_Store"]


# -- Options for HTML output -------------------------------------------------

# The theme to use for HTML and HTML Help pages. See the documentation for
# a list of builtin themes.
#
html_theme = "alabaster"

# Add any paths that contain custom static files (such as style sheets) here,
# relative to this directory. They are copied after the builtin static files,
# so a file named "default.css" will overwrite the builtin "default.css".
html_static_path = []
55 changes: 55 additions & 0 deletions docs/index.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
.. pysegmenttree documentation master file, created by
sphinx-quickstart on Sat Nov 13 22:43:44 2021.
You can adapt this file completely to your liking, but it should at least
contain the root `toctree` directive.
pysegmenttree
=============
**Segment tree** is a data structure to perform efficient range queries over an array.

For example, finding the sum/minimum/maximum of the arbitrary continuous interval in `O(Log[N])` time.
Logariphmic time complexity is achieved by storing the original input data in a tree like data structure with some additional precalculated data.

This library implementation is primarly inspired by this beatiful article_.

.. _article: https://codeforces.com/blog/entry/18051


Methods complexity
------------------

Considering that input array has `N` elements.


.. table::
:widths: auto

=========== =============== ================
Method Time complexity Space complexity
=========== =============== ================
constructor O(N) O(2*N)
query O(Log[N]) O(1)
update O(Log[N]) O(1)
=========== =============== ================


Source code
-----------

The project is hosted on GitHub_.

.. _GitHub: https://github.com/greshilov/pysegmenttree


.. toctree::
pysegmenttree
:maxdepth: 2



Indices and tables
==================

* :ref:`genindex`
* :ref:`modindex`
* :ref:`search`
35 changes: 35 additions & 0 deletions docs/make.bat
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
@ECHO OFF

pushd %~dp0

REM Command file for Sphinx documentation

if "%SPHINXBUILD%" == "" (
set SPHINXBUILD=sphinx-build
)
set SOURCEDIR=.
set BUILDDIR=_build

if "%1" == "" goto help

%SPHINXBUILD% >NUL 2>NUL
if errorlevel 9009 (
echo.
echo.The 'sphinx-build' command was not found. Make sure you have Sphinx
echo.installed, then set the SPHINXBUILD environment variable to point
echo.to the full path of the 'sphinx-build' executable. Alternatively you
echo.may add the Sphinx directory to PATH.
echo.
echo.If you don't have Sphinx installed, grab it from
echo.https://www.sphinx-doc.org/
exit /b 1
)

%SPHINXBUILD% -M %1 %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% %O%
goto end

:help
%SPHINXBUILD% -M help %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% %O%

:end
popd
86 changes: 86 additions & 0 deletions docs/pysegmenttree.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
=========
Reference
=========

.. module:: pysegmenttree


stree
=====

.. function:: stree(source: List[T], func: Optional[Callable[[T, T], T]] = None) -> AbstractSegmentTree

Function that returns a best suitable version of the segment tree for the given input.

>>> st = stree([0, 1, 2, 3])
>>> type(st)
<pysegmenttree.c_extensions.IntSegmentTree object at 0x7f4b0c8dfc50>

>>> st = stree([0.0, 1.0, 2.0, 3.0])
>>> type(st)
<pysegmenttree.c_extensions.FloatSegmentTree object at 0x7f4b0c8dfdb0>

>>> st = stree([0, 1, 2, 3], func=min)
>>> type(st)
<pysegmenttree._pysegmenttree_py.PySegmentTree object at 0x7f4b0c9a18e0>


PySegmentTree
=============

.. class:: PySegmentTree(source: List[T], func: Optional[Func] = None)

Creates a segment tree instance.

**func** is a function that will be used in `query` method.
Must be a function with two arguments `T`, returning `T`(Type interface is `Callable[[T, T], T]`).

>>> st = PySegmentTree([1.5, 1, 0, 2], func=min)

.. method:: len(st)

Return the number of items in segment tree *st*.

>>> len(st)
4


.. method:: query(start: int, end: int) -> Optional[T]

Performs a query operation on the interval [**start**, **end**) with the function chosen during the creation.
Note, that **end** is not included. Behaviour is replicated from the python slice operator.

>>> st.query(0, 2)
1
>>> st.query(0, 4)
0


.. method:: update(i: int, value: T)

Set i-th element of the tree to the specified value **value**.

>>> st.update(0, -100)
>>> st.query(0, 2)
-100


IntSegmentTree
==============

.. class:: IntSegmentTree(source: List[int], func: Optional[str] = None)

Typed version of the :class:`PySegmentTree` implemented in C using `long long int` type.
The behavior is the same as for :class:`PySegmentTree` except few moments:

- **func** argument in the constructor has `str` type and currently doesn't affect anything. This type of tree is always `sum` tree.
- Raises :exc:`OverflowError` if any element exceeds `long long` type range.
- Much faster than :class:`PySegmentTree`.


FloatSegmentTree
================

.. class:: FloatSegmentTree(source: List[float], func: Optional[str] = None)

Same as :class:`IntSegmentTree`, except it uses `double` C-type under the hood.
5 changes: 3 additions & 2 deletions requirements.dev.in
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
black
black==21.10b0
isort~=5.10
mypy
mypy~=0.9
pre-commit~=2.15
pytest~=6.0
pytest-cov~=3.0
pip-tools~=6.4
sphinx~=4.3
tabulate~=0.8
Loading

0 comments on commit c6d3f99

Please sign in to comment.