KCParser 1.0.6
A lightweight string equation parser built with Regular Expressions
Requires Python: >=3.6

# KCParser
**Contents**
- [Syntax: functions](#functions)
  - [Syntax: sigma and pi](#additional-information-on-sigma-and-pi-usage) 
- [Syntax: constants](#constants) 
- [Installation and implementation](#installation-and-implementation)

---

### _String expressions; regular expressions_

KCParser is a small package designed to make parsing mathematical expressions, given as strings, easier. The package uses regular expressions to do so and has its own simple syntax.

### Features

- 21 mathematical functions, including summation, product, and trigonometric functions.
- 37 mathematical constants, including the golden ratio, the universal parabolic constant, and Feigenbaum's constants.
- An easy and simple-to-learn syntax.
- An easy-going license perfect for any project, big or small.
- A range of descriptive, helpful, yet short syntax exception descriptions.

### Syntax Guide

#### General
In general, expressions should be written in the same manner as to how you would write a normal mathematical expression e.g. `5+(3*2)`. It should be noted that during the lifespan of `KCParser.__init__(self, expr)`, a nested function named `gpm` is ran, altering `self.expr`. This is the _general product modifier_ function, and is useful for dealing with the multiple notations for multiplication. For example, `)(` will become `)*(`, `3sin(0.5)` will become `3*sin(0.5)`, etc.

#### Functions
KCParser comes with 21 mathematical functions. To use these functions, you should always include parantheses around their input values, as this is to comply with KCParser syntax e.g. `sin(0.5)`, not `sin0.5`. 

**The following is a list of recognised functions in KCParser**:
| syntax | name | description |
| --- | --- | --- |
| `n!` | Factorial | ![equation](https://user-images.githubusercontent.com/98128904/161534129-0514be0d-1349-47ba-b185-e3c86b18d147.png) |
| `abs(n)` | Absolute value | The absolute value of `n` |
| `sqrt(n)` | Square root | `n` to the power of `0.5`
| `root(n,x)` | xth root | `n` to the power of `1/x` |
| `ncr(n,r)` | n choose r | From [_pascal's triangle_](https://en.wikipedia.org/wiki/Pascal%27s_triangle), choose `n`th number from row `r`.
| `npr(n,r)` | Permutation | The permutation of the arrangement of `r` objects from a set of `n` objects. |
| `sigma(i,n,expr)` | Summation | ![equation](https://user-images.githubusercontent.com/98128904/161524237-9f1875da-7a84-4c6f-8851-63b874649c10.png) |
| `pi(i,n,expr)` | Product | ![equation](https://user-images.githubusercontent.com/98128904/161532455-f595e5fd-11dd-46b8-8b27-a57348c70db4.png) |
| `ln(x)` | Natural logarithm | The logarithm of `x` to the base e. |
| `log(x,b)` | Logarithm | The logarithm of `x` to the base `b` |
| `sin(x)` | Sine | Sine of `x` (rad). |
| `asin(x)` | Arcsine | Arcsine of `x` (rad). |
| `csc(x)` | Cosecant | Cosecant of `x` (rad). |
| `sinh(x)` | Hyperbolic Sine | Hyperbolic sine of `x` (rad). |
| `cos(x)` | Cosine | Cosine of `x` (rad). |
| `acos(x)` | Arccosine | Arccosine of `x` (rad). |
| `sec(x)` | Secant | Secant of `x` (rad). |
| `cosh(x)` | Hyperbolic Cosine | Hyperbolic cosine of `x` (rad). |
| `tan(x)` | Tangent | Tangent of `x` (rad). |
| `atan(x)` | Arctangent | Arctangent of `x` (rad). |
| `cot(x)` | Cotangent | Cotangent of `x` (rad). |
| `tanh(x)` | Hyperbolic Tangent | Hyperbolic tangent of `x` (rad). |

##### _Additional information on sigma and pi usage_
The sigma and pi functions can use a special character, `#`. In KCParser, this is the _incremental operator_.
```py
for x in range(int(start), int(end) + 1):
    cexpr = expr.replace("#", str(x))
    cexpr = self.__eval_brackets(cexpr)
    result += self.__calc(cexpr)
    ...
```
As you can see, the current expression is set to `expr` where the incremental operator is replaced with the current iteration of the for loop. For example, `sigma(1,5,#)` would process like so:
```py
cexpr = expr.replace("#", x)  # x = 1
cexpr = self.__eval_brackets(cexpr)
result += self.__calc(cexpr)  # result = 1
cexpr = expr.replace("#", x)  # x = 2
cexpr = self.__eval_brackets(cexpr)
result += self.__calc(cexpr)  # result = 3
cexpr = expr.replace("#", x)  # x = 3
cexpr = self.__eval_brackets(cexpr)
result += self.__calc(cexpr)  # result = 6
cexpr = expr.replace("#", x)  # x = 4
cexpr = self.__eval_brackets(cexpr)
result += self.__calc(cexpr)  # result = 10
cexpr = expr.replace("#", x)  # x = 5
cexpr = self.__eval_brackets(cexpr)
result += self.__calc(cexpr)  # result = 15
```
Thus, the final answer of `sigma(1,5,#)` is 15. Therefore, we can say that the following is true:

![equation](https://user-images.githubusercontent.com/98128904/161535383-a01af9c1-ca3f-4e7a-9c16-fd8138d3f32a.png)

![equation](https://user-images.githubusercontent.com/98128904/161535630-32f7c7de-58af-4dc0-9ce5-0dc020d5c92d.png)

#### Constants
KCParser comes with a `CONSTANTS` dictionary containing 37 mathematical constants. To use these constants within a string expression, you must use the `[]` syntax: 
- `[const_name]` - replaced by the string value of `CONSTANTS[const_name]` during parisng e.g. `7+[e]` -> `7+2.7...`.

**The following is a list of `const_name` values accepted by KCParser**:

| const_name | value | description |
| --- | --- | --- |
| pi | 3.141592653589793 | Archimedes' constant, Pi |
| e | 2.718281828459045 | Euler's number, e
| em | 0.577215664901533 | Euler-Mascheroni constant |
| golden | 1.6180339887498948 | The golden ratio
| mm | 0.261497212847643 | Meissel-Mertens constant |
| bernstein | 0.280169499023869 | Bernstein's constant |
| gkw | 0.303663002898733 | Gauss-Kuzmin-Wirsing constant |
| hsm | 0.3532363718549960 | Hafner-Sarnak-McCurley constant |
| omega | 0.5671432904097839 | Omega constant
| gd | 0.624329988543551 | Golomb-Dickman constant |
| cahen | 0.6434105462 | Cahen's constant |
| tp | 0.660161815846870 | Twin prime constant |
| laplace | 0.662743419349182 | The laplace limit |
| et | 0.70258 | Embree-Trefethen constant |
| lr | 0.764223653589221 | Landau-Ramanujan constant |
| brunpq | 0.87058838 | Brun's constant for prime quadruplets |
| brunpt | 1.902160583104 | Brun's constant for prime twins |
| catalan | 0.9159655941772190 | Catalan's constant |
| viswanath | 1.13198824 | Viswanath's constant |
| apery | 1.202056903159594 | Apéry's constant |
| conway | 1.303577269034297 | Conway's constant |
| mills | 1.306377883863081 | Mills' constant |
| plastic | 1.3247179572447460 | The plastic number |
| rs | 1.4513692348833811 | Ramanujan-Soldner constant |
| backhouse | 1.456074948582690 | Backhouse's constant |
| porter | 1.467078079433975 | Porter's constant |
| lieb | 1.4670780794 | Lieb's square ice constant |
| eb | 1.606695152415292 | Erdős–Borwein constant |
| niven | 1.705211140105368 | Niven's constant |
| upc | 2.2955871493926381 | The universal parabolic constant |
| feigenbauma | 2.5029078750958929 | Feigenbaum's alpha constant |
| feigenbaumd | 4.6692016091029907 | Feigenbaum's delta constant |
| sierpinski | 2.584981759579253 | Sierpinski's constant |
| khinchin | 2.685452001065307 | Khinchin's constant |
| fr | 2.807770242028519 | Fransén–Robinson constant |
| levy | 3.275822918721811 | Lévy's constant |
| rf | 3.359885666243178 | The sum of the reciprocals of the fibonacci sequence |

##### _Special case: [ans]_
Whilst not a constant, and not included in the constant table, the `[ans]` syntax follows the same syntax as constants: when writing an expression, you can use `[ans]` to access the result of the most recent calculation e.g. `5*([ans]+[e])`. **By default, `[ans]` is 0**.

### Installation and implementation

Do `pip install KCParser` in a command line to install KCParser. In your project, use `from KCParser.KCParser import KCParser` to import the KCParser class.

**The following is an example of implementing and using the KCParser class**:
```py
expression = input("Please enter a mathematical expression: ")  # e.g. 5 + [pi]
p = KCParser(expression)
ans = p.parse()
print(ans)
# >>> 8.14...
```

**KCParser objects can be operated on like regular mathematical expressions**:
```py
p1 = KCParser("3+2")
p2 = KCParser("[pi]!")
p3 = p1 / p2
# p3.expr = "((3+2)/(3.141592653589793!))"
```
**[You can view a demo program for KCParser here!](https://replit.com/@KCatterall/KCParser-Demo)**

_[Back to top](#kcparser)_