# 解方程

## 简单的一元一次方程

\begin{equation}x + 16 = -25\end{equation}

\begin{equation}x + 16 - 16 = -25 - 16\end{equation}

\begin{equation}x = -25 - 16\end{equation}

\begin{equation}x = -41\end{equation}

```python
x = -41                # 验证方程的解
x + 16 == -25
```

    True

## 带系数的方程

\begin{equation}3x - 2 = 10 \end{equation}

\begin{equation}3x - 2 + 2 = 10 + 2 \end{equation}

\begin{equation}3x = 12 \end{equation}

\begin{equation}x = 4\end{equation}

```python
x = 4                  # 代入 x = 4
3 * x - 2 == 10
```

    True

## 系数是分数的方程

\begin{equation}\frac{x}{3} + 1 = 16 \end{equation}

\begin{equation}\frac{x}{3} = 15 \end{equation}

\begin{equation}\frac{3}{1} \cdot \frac{x}{3} = 15 \cdot 3 \end{equation}

\begin{equation}x = 45 \end{equation}

```python
x = 45
x/3 + 1 == 16
```

    True

## 需要合并同类项的例子

\begin{equation}3x + 2 = 5x - 1 \end{equation}

\begin{equation}3x + 3 = 5x \end{equation}

\begin{equation}3 = 2x \end{equation}

\begin{equation}\frac{3}{2} = x \end{equation}

\begin{equation}x = \frac{3}{2} \end{equation}

\begin{equation}x = 1\frac{1}{2} \end{equation}

```python
x = 1.5
3*x + 2 == 5*x -1
```

    True

## 一元方程练习

\begin{equation}\textbf{4(x + 2)} + \textbf{3(x - 2)} = 16 \end{equation}

\begin{equation}4x + 8 + 3x - 6 = 16 \end{equation}

\begin{equation}7x + 2 = 16 \end{equation}

\begin{equation}7x = 14 \end{equation}

\begin{equation}\frac{7x}{7} = \frac{14}{7} \end{equation}

\begin{equation}x = 2 \end{equation}

```python
x = 2
4 * (x + 2) + 3 * (x - 2) == 16
```

    True

# 线性方程

## 例子

\begin{equation}2y + 3 = 3x - 1 \end{equation}

\begin{equation}2y + 4 = 3x \end{equation}

\begin{equation}2y = 3x - 4 \end{equation}

\begin{equation}y = \frac{3x - 4}{2} \end{equation}

```python
import numpy as np
from tabulate import tabulate

x = np.array(range(-10, 11))  # 从 -10 到 10 的21个数据点
y = (3 * x - 4) / 2           # 对应的函数值

print(tabulate(np.column_stack((x,y)), headers=['x', 'y']))
```

      x      y
    ---  -----
    -10  -17
     -9  -15.5
     -8  -14
     -7  -12.5
     -6  -11
     -5   -9.5
     -4   -8
     -3   -6.5
     -2   -5
     -1   -3.5
      0   -2
      1   -0.5
      2    1
      3    2.5
      4    4
      5    5.5
      6    7
      7    8.5
      8   10
      9   11.5
     10   13

```python
from IPython.core.interactiveshell import InteractiveShell
InteractiveShell.ast_node_interactivity = "last_expr"
# %matplotlib inline
```

```python
from matplotlib import pyplot as plt

plt.plot(x, y, color="grey", marker = "o")
plt.xlabel('x')
plt.ylabel('y')
plt.grid()
plt.show()
```

## 截距

```python
plt.plot(x, y, color="grey")
plt.xlabel('x')
plt.ylabel('y')
plt.grid()
plt.axhline()                # 画出坐标轴
plt.axvline()
plt.show()
```

- x轴上的截距

\begin{equation}0 = \frac{3x - 4}{2} \end{equation}

\begin{equation}\frac{3x - 4}{2} = 0 \end{equation}

\begin{equation}3x - 4 = 0 \end{equation}

\begin{equation}3x = 4 \end{equation}

\begin{equation}x = \frac{4}{3} \end{equation}

\begin{equation}x = 1\frac{1}{3} \end{equation}

- y轴上的截距

\begin{equation}y = \frac{3\cdot0 - 4}{2} \end{equation}

\begin{equation}y = \frac{-4}{2} \end{equation}

\begin{equation}y = -2 \end{equation}

```python
plt.plot(x, y, color="grey")
plt.xlabel('x')
plt.ylabel('y')
plt.grid()
plt.axhline()
plt.axvline()
plt.annotate('x',(1.333, 0)) # 标出截距点
plt.annotate('y',(0,-2))
plt.show()
```

> 截距的作用是明显的：两点成一线。连接截距就可以画出函数曲线。

## 斜率

\begin{equation}slope = \frac{\Delta{y}}{\Delta{x}} \end{equation}

\begin{equation}m = \frac{y_{2} - y_{1}}{x_{2} - x_{1}} \end{equation}

\begin{equation}m = \frac{7 - -2}{6 - 0} \end{equation}

\begin{equation}m = \frac{7 + 2}{6 - 0} \end{equation}

\begin{equation}m = 1.5 \end{equation}

```python
plt.plot(x, y, color="grey")
plt.xlabel('x')
plt.ylabel('y')
plt.grid()
plt.axhline()
plt.axvline()
m = 1.5
xInt = 4 / 3
yInt = -2
mx = [0, xInt]
my = [yInt, yInt + m * xInt]
plt.plot(mx, my, color='red', lw=5)  # 用红色标出
plt.show()
```

```python
plt.grid()                             # 放大图
plt.axhline()
plt.axvline()
m = 1.5
xInt = 4 / 3
yInt = -2
mx = [0, xInt]
my = [yInt, yInt + m * xInt]
plt.plot(mx, my, color='red', lw=5)
plt.show()
```

### 直线的斜率、截距形式

\begin{equation}y = mx + b \end{equation}

\begin{equation}y = \frac{3x - 4}{2} \end{equation}

\begin{equation}y = 1\frac{1}{2}x + -2 \end{equation}

```python
m = 1.5
yInt = -2

x = np.array(range(-10, 11))
y2 = m * x + yInt                       # 斜率截距形式

plt.plot(x, y2, color="grey")
plt.xlabel('x')
plt.ylabel('y')
plt.grid()
plt.axhline()
plt.axvline()

plt.annotate('y', (0, yInt))
plt.show()
```

# 线形方程组
> 解的含义：直线的交点

\begin{equation}x + y = 16 \end{equation}
\begin{equation}10x + 25y = 250 \end{equation}

```python
l1p1 = [16, 0]  # 线1点1
l1p2 = [0, 16]  # 线1点2

l2p1 = [25,0]   # 线2点1
l2p2 = [0,10]   # 线2点2

plt.plot(l1p1,l1p2, color='blue')
plt.plot(l2p1, l2p2, color="orange")
plt.xlabel('x')
plt.ylabel('y')
plt.grid()

plt.show()
```

### 解线形方程组 （消去法）
\begin{equation}x + y = 16 \end{equation}
\begin{equation}10x + 25y = 250 \end{equation}

\begin{equation}-10(x + y) = -10(16) \end{equation}
\begin{equation}10x + 25y = 250 \end{equation}

\begin{equation}-10x + -10y = -160 \end{equation}
\begin{equation}10x + 25y = 250 \end{equation}

\begin{equation}15y = 90 \end{equation}
\begin{equation}y = \frac{90}{15} \end{equation}
\begin{equation}y = 6 \end{equation}

\begin{equation}x + 6 = 16 \end{equation}
\begin{equation}x = 10 \end{equation}

```python
x = 10
y = 6
print ((x + y == 16) & ((10 * x) + (25 * y) == 250))
```

    True

# 指数、根和对数

## 指数
\begin{equation}2^{2} = 2 \cdot 2 = 4\end{equation}

\begin{equation}2^{3} = 2 \cdot 2 \cdot 2 = 8\end{equation}

```python
x = 5**3
print(x)
```

    125

## 根

\begin{equation}?^{2} = 9 \end{equation}

\begin{equation}\sqrt{9} = 3 \end{equation}

\begin{equation}\sqrt[3]{64} = 4 \end{equation}

```python
import math

x = math.sqrt(9)            # 平方根
print (x)

cr = round(64 ** (1. / 3))   # 立方根
print(cr)
```

    3.0
    4

### 根是分数形式的指数

\begin{equation} 8^{\frac{1}{3}} = \sqrt[3]{8} = 2 \end{equation}

\begin{equation} 9^{\frac{1}{2}} = \sqrt{9} = 3 \end{equation}

```python
print (9**0.5)
print (math.sqrt(9))
```

    3.0
    3.0

## 对数
> 对数是指数的逆运算

\begin{equation}4^{?} = 16 \end{equation}

\begin{equation}log_{4}(16) = 2 \end{equation}

```python
x = math.log(16, 4)
print(x)
```

    2.0

### 以10为底的对数

\begin{equation}log(64) = 1.8061 \end{equation}

### 自然对数
\begin{equation}log_{e}(64) = ln(64) = 4.1589 \end{equation}

```python
print(math.log10(64))

print (math.log(64))
```

    1.806179973983887
    4.1588830833596715

## 幂运算 （合并同类项）

\begin{equation}2y = 2x^{4} ( \frac{x^{2} + 2x^{2}}{x^{3}} ) \end{equation}

\begin{equation}2y = 2x^{4} ( \frac{3x^{2}}{x^{3}} ) \end{equation}

\begin{equation}2y = 2x^{4} ( 3x^{-1} ) \end{equation}

\begin{equation}2y = 6x^{3} \end{equation}

\begin{equation}y = 3x^{3} \end{equation}

```python
x = np.array(range(-10, 11))
y3 = 3 * x ** 3

print(tabulate(np.column_stack((x, y3)), headers=['x', 'y']))
```

      x      y
    ---  -----
    -10  -3000
     -9  -2187
     -8  -1536
     -7  -1029
     -6   -648
     -5   -375
     -4   -192
     -3    -81
     -2    -24
     -1     -3
      0      0
      1      3
      2     24
      3     81
      4    192
      5    375
      6    648
      7   1029
      8   1536
      9   2187
     10   3000

```python
plt.plot(x, y3, color="magenta")  # y3是曲线
plt.xlabel('x')
plt.ylabel('y')
plt.grid()
plt.axhline()
plt.axvline()
plt.show()
```

### 看一个成指数增长的例子

\begin{equation}y = 2^{x} \end{equation}

```python
y4 = 2.0**x
plt.plot(x, y4, color="magenta")
plt.xlabel('x')
plt.ylabel('y')
plt.grid()
plt.axhline()
plt.axvline()
plt.show()
```

### 复利计算

> 存款100，年利5%，20年后余额是多少（记复利）

\begin{equation}y1 = 100 + (100 \cdot 0.05) \end{equation}

\begin{equation}y1 = 100 \cdot 1.05 \end{equation}

\begin{equation}y2 = 100 \cdot 1.05 \cdot 1.05 \end{equation}

\begin{equation}y2 = 100 \cdot 1.05^{2} \end{equation}

\begin{equation}y20 = 100 \cdot 1.05^{20} \end{equation}

```python
year = np.array(range(1, 21))                      # 年份
balance = 100 * (1.05 ** year)                     # 余额
plt.plot(year, balance, color="green")
plt.xlabel('Year')
plt.ylabel('Balance')
plt.show()
```

# 多项式

\begin{equation}12x^{3} + 2x - 16 \end{equation}

三项：
- 12x3
- 2x
- -16

- 两个系数(12 和 2) 和一个常量-16
- 变量 x
- 指数 3

## 标准形式
随着x的指数增长排列（升幂）
\begin{equation}3x + 4xy^{2} - 3 + x^{3} \end{equation}

指数最高项在前（降幂）
\begin{equation}x^{3} + 4xy^{2} + 3x - 3 \end{equation}

## 多项式化简

\begin{equation}x^{3} + 2x^{3} - 3x - x + 8 - 3 \end{equation}

\begin{equation}3x^{3} - 4x + 5 \end{equation}

```python
from random import randint
x = randint(1,100)                  # 取任意值验证多项式化简

(x**3 + 2*x**3 - 3*x - x + 8 - 3) == (3*x**3 - 4*x + 5)
```

    True

## 多项式相加

\begin{equation}(3x^{3} - 4x + 5)   +   (2x^{3} + 3x^{2} - 2x + 2) \end{equation}

\begin{equation}3x^{3} + 2x^{3} + 3x^{2} - 4x -2x + 5 + 2 \end{equation}

\begin{equation}5x^{3} + 3x^{2} - 6x + 7 \end{equation}

```python
x = randint(1,100)

(3*x**3 - 4*x + 5) + (2*x**3 + 3*x**2 - 2*x + 2) == 5*x**3 + 3*x**2 - 6*x + 7
```

    True

## 多项式相减

\begin{equation}(2x^{2} - 4x + 5)   -   (x^{2} - 2x + 2) \end{equation}

\begin{equation}(2x^{2} - 4x + 5)   +   (-x^{2} + 2x - 2) \end{equation}

\begin{equation}2x^{2} + -x^{2} + -4x + 2x + 5 + -2 \end{equation}

\begin{equation}x^{2} - 2x + 3 \end{equation}

```python
from random import randint
x = randint(1,100)

(2*x**2 - 4*x + 5) - (x**2 - 2*x + 2) == x**2 - 2*x + 3
```

    True

## 多项式相乘

1. 用第一个多项式的每一项乘以第二个多项式
2. 把相乘的结果合并同类项

\begin{equation}(x^{4} + 2)(2x^{2} + 3x - 3) \end{equation}

\begin{equation}2x^{6} + 3x^{5} - 3x^{4} + 4x^{2} + 6x - 6 \end{equation}

```python
x = randint(1,100)

(x**4 + 2)*(2*x**2 + 3*x - 3) == 2*x**6 + 3*x**5 - 3*x**4 + 4*x**2 + 6*x - 6
```

    True

## 多项式相除

### 简单例子

\begin{equation}(4x + 6x^{2}) \div 2x \end{equation}

\begin{equation}\frac{4x + 6x^{2}}{2x} \end{equation}

\begin{equation}\frac{4x}{2x} + \frac{6x^{2}}{2x}\end{equation}

\begin{equation}2 + 3x\end{equation}

```python
x = randint(1,100)

(4*x + 6*x**2) / (2*x) == 2 + 3*x
```

    True

### 长除法

\begin{equation}(x^{2} + 2x - 3) \div (x - 2) \end{equation}

\begin{equation} x - 2 |\overline{x^{2} + 2x - 3} \end{equation}

\begin{equation} \;\;\;\;x \end{equation}
\begin{equation}x - 2 |\overline{x^{2} + 2x - 3} \end{equation}
\begin{equation} \;x^{2} -2x \end{equation}

\begin{equation} \;\;\;\;x \end{equation}
\begin{equation}x - 2 |\overline{x^{2} + 2x - 3} \end{equation}
\begin{equation}- (x^{2} -2x) \end{equation}
\begin{equation}\;\;\;\;\;\overline{\;\;\;\;\;\;\;\;\;\;4x -3} \end{equation}

\begin{equation} \;\;\;\;\;\;\;\;x + 4 \end{equation}
\begin{equation}x - 2 |\overline{x^{2} + 2x - 3} \end{equation}
\begin{equation}- (x^{2} -2x) \end{equation}
\begin{equation}\;\;\;\;\;\overline{\;\;\;\;\;\;\;\;\;\;4x -3} \end{equation}
\begin{equation}- (\;\;\;\;\;\;\;\;\;\;\;\;4x -8) \end{equation}
\begin{equation}\;\;\;\;\;\overline{\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;5} \end{equation}

\begin{equation}x + 4 + \frac{5}{x-2} \end{equation}

```python
x = randint(3,100)

(x**2 + 2*x -3)/(x-2) == x + 4 + (5/(x-2))

```

    True

# 因式

16可以如下表示
- 1 x 16
- 2 x 8
- 4 x 4

或者 1, 2, 4, 8 是 16 的因子

## 用多项式乘来表示多项式

\begin{equation}-6x^{2}y^{3} \end{equation}

\begin{equation}(2xy^{2})(-3xy) \end{equation}

又如

\begin{equation}(x + 2)(2x^{2} - 3y + 2) = 2x^{3} + 4x^{2} - 3xy + 2x - 6y + 4 \end{equation}

那么**x+2** 和 **2x2 - 3y + 2** 都是 **2x3 + 4x2 - 3xy + 2x - 6y + 4**的因子

## 最大公共因子

|   16   |   24   |
|--------|--------|
| 1 x 16 | 1 x 24 |
| 2 x 8 | 2 x 12 |
| 2 x **8**  | 3 x **8**  |
| 4 x 4  | 4 x 6  |

8是16和24的最大公约数

\begin{equation}15x^{2}y\;\;\;\;\;\;\;\;9xy^{3}\end{equation}

这两个多项式的最大公共因子是?

## 最大公共因子

先看系数，他们都包含**3**
- 3 x 5 = 15
- 3 x 3 = 9

再看***x***项， x2 和 x。

最后看***y***项, y 和 y3。

最大公共因子是
\begin{equation}3xy\end{equation}

## 最大公共因子

可见最大公共因子总包括

- 系数的最大公约数
- 变量指数的最小值

用多项式除来验证：

\begin{equation}\frac{15x^{2}y}{3xy}\;\;\;\;\;\;\;\;\frac{9xy^{3}}{3xy}\end{equation}

\begin{equation}3xy(5x) = 15x^{2}y\end{equation}
\begin{equation}3xy(3y^{2}) = 9xy^{3}\end{equation}

```python
x = randint(1,100)
y = randint(1,100)

print((3*x*y)*(5*x) == 15*x**2*y)
print((3*x*y)*(3*y**2) == 9*x*y**3)
```

    True
    True

## 用系数最大公约数作因式分解

\begin{equation}6x + 15y \end{equation}

\begin{equation}6x + 15y = 3(2x) + 3(5y) \end{equation}

\begin{equation}6x + 15y = 3(2x) + 3(5y) = \mathbf{3(2x + 5y)} \end{equation}

```python
x = randint(1,100)
y = randint(1,100)

(6*x + 15*y) == (3*(2*x) + 3*(5*y)) == (3*(2*x + 5*y))
```

    True

## 用最大公共因子作因式分解
\begin{equation}15x^{2}y + 9xy^{3}\end{equation}

\begin{equation}3xy(5x) = 15x^{2}y\end{equation}
\begin{equation}3xy(3y^{2}) = 9xy^{3}\end{equation}

\begin{equation}15x^{2}y + 9xy^{3} = \mathbf{3xy(5x + 3y^{2})}\end{equation}

```python
x = randint(1,100)
y = randint(1,100)

(15*x**2*y + 9*x*y**3) == (3*x*y*(5*x + 3*y**2))
```

    True

## 用平方差公式作因式分解

\begin{equation}x^{2} - 9\end{equation}

\begin{equation}x^{2} - 3^{2}\end{equation}

\begin{equation}(x - 3)(x + 3)\end{equation}

```python
x = randint(1,100)

(x**2 - 9) == (x - 3)*(x + 3)
```

    True

## 用平方作因式分解
\begin{equation}x^{2} + 10x + 25\end{equation}

\begin{equation}(x + 5)(x + 5)\end{equation}

\begin{equation}(x + 5)^{2}\end{equation}

一般的
\begin{equation}(a + b)^{2} = a^{2} + b^{2}+ 2ab \end{equation}

```python
a = randint(1,100)
b = randint(1,100)

a**2 + b**2 + (2*a*b) == (a + b)**2
```

    True

# 二次方程

\begin{equation}y = 2(x - 1)(x + 2)\end{equation}

\begin{equation}y = 2x^{2} + 2x - 4\end{equation}

```python
x = np.array(range(-9, 9))
y = 2 * x **2 + 2 * x - 4
plt.plot(x, y, color="grey")  # 画二次曲线 （抛物线）
plt.xlabel('x')
plt.ylabel('y')
plt.grid()
plt.axhline()
plt.axvline()
plt.show()
```

>会是什么形状？

\begin{equation}y = -2x^{2} + 6x + 7\end{equation}

```python
x = np.array(range(-8, 12))
y = -2 * x ** 2 + 6 * x + 7
plt.plot(x, y, color="grey")
plt.xlabel('x')
plt.ylabel('y')
plt.grid()
plt.axhline()
plt.axvline()
plt.show()
```

## 抛物线的顶点
\begin{equation}y = ax^{2} + bx + c\end{equation}

***a***, ***b***, ***c***是系数

它产生的抛物线有顶点，或者是最高点，或者是最低点。

```python
def plot_parabola(a, b, c):
    vx = (-1*b)/(2*a)              # 顶点
    vy = a*vx**2 + b*vx + c

    minx = int(vx - 10)            # 范围
    maxx = int(vx + 11)
    x = np.array(range(minx, maxx))
    y = a * x ** 2 + b * x + c
    miny = y.min()
    maxy = y.max()

    plt.plot(x, y, color="grey")    # 画曲线
    plt.xlabel('x')
    plt.ylabel('y')
    plt.grid()
    plt.axhline()
    plt.axvline()

    sx = [vx, vx]                   # 画中心线
    sy = [miny, maxy]
    plt.plot(sx, sy, color='magenta')

    plt.scatter(vx,vy, color="red") # 画顶点

```

```python
plot_parabola(2, 2, -4)
plt.show()
plot_parabola(-2, 3, 5)
plt.show()
```

## 抛物线的交点（二次方程的解）

\begin{equation}y = 2(x - 1)(x + 2)\end{equation}

\begin{equation}2(x - 1)(x + 2) = 0\end{equation}

\begin{equation}x = 1\end{equation}

\begin{equation}x = -2\end{equation}

```python
# 画曲线
plot_parabola(2, 2, -4)

# 画交点
x1 = -2
x2 = 1
plt.scatter([x1,x2],[0,0], color="green")
plt.annotate('x1',(x1, 0))
plt.annotate('x2',(x2, 0))

plt.show()

```

## 二次方程的解公式
\begin{equation}ax^{2} + bx + c = 0\end{equation}

\begin{equation}x = \frac{-b \pm \sqrt{b^{2} - 4ac}}{2a}\end{equation}

```python
def plot_parabola_from_formula (a, b, c):
    plot_parabola(a, b, c)                      # 画曲线

    x1 = (-b + (b*b - 4*a*c)**0.5)/(2 * a)
    x2 = (-b - (b*b - 4*a*c)**0.5)/(2 * a)

    plt.scatter([x1, x2], [0, 0], color="green") # 画解
    plt.annotate('x1', (x1, 0))
    plt.annotate('x2', (x2, 0))
    plt.show()

plot_parabola_from_formula (2, -16, 2)
```

# 函数

\begin{equation}f(x) = x^{2} + 2\end{equation}

\begin{equation}f(3) = 11\end{equation}

```python
def f(x):
    return x**2 + 2

f(3)
```

    11

```python
x = np.array(range(-100, 101))

plt.xlabel('x')
plt.ylabel('f(x)')
plt.grid()

plt.plot(x, f(x), color='purple')

plt.show()
```

## 函数的定义域

\begin{equation}f(x) = x + 1, \{x \in \rm I\!R\}\end{equation}

\begin{equation}g(x) = (\frac{12}{2x})^{2}, \{x \in \rm I\!R\;\;|\;\; x \ne 0 \}\end{equation}

简化形式：
\begin{equation}g(x) = (\frac{12}{2x})^{2},\;\; x \ne 0\end{equation}

```python
def g(x):
    if x != 0:
        return (12/(2*x))**2

x = range(-100, 101)
y = [g(a) for a in x]

print(g(0.1))
plt.xlabel('x')
plt.ylabel('g(x)')
plt.grid()
plt.plot(x, y, color='purple')

# 绘制临界点， 如果取接近0的值，临界点附件函数的形状变得不可见
plt.plot(0, g(1), color='purple', marker='o', markerfacecolor='w', markersize=8)
plt.show()
```

\begin{equation}h(x) = 2\sqrt{x}, \{x \in \rm I\!R\;\;|\;\; x \ge 0 \}\end{equation}

```python
def h(x):
    if x >= 0:
        return 2 * np.sqrt(x)

x = range(-100, 101)
y = [h(a) for a in x]

plt.xlabel('x')
plt.ylabel('h(x)')
plt.grid()

plt.plot(x, y, color='purple')
# 画出边界
plt.plot(0, h(0), color='purple', marker='o', markerfacecolor='purple', markersize=8)

plt.show()
```

\begin{equation}j(x) = x + 2,\;\; x \ge 0 \text{ and } x \le 5\end{equation}

\begin{equation}\{x \in \rm I\!R\;\;|\;\; 0 \le x \le 5 \}\end{equation}

```python
def j(x):
    if x >= 0 and x <= 5:
        return x + 2

x = range(-100, 101)
y = [j(a) for a in x]

plt.xlabel('x')
plt.ylabel('j(x)')
plt.grid()

plt.plot(x, y, color='purple')

# 两个边界点
plt.plot(0, j(0), color='purple', marker='o', markerfacecolor='purple', markersize=8)
plt.plot(5, j(5), color='purple', marker='o', markerfacecolor='purple', markersize=8)

plt.show()
```

### 阶梯函数

\begin{equation}
k(x) = \begin{cases}
  0, & \text{if } x = 0, \\
  1, & \text{if } x = 100
\end{cases}
\end{equation}

```python
def k(x):
    if x == 0:
        return 0
    elif x == 100:
        return 1

x = range(-100, 101)
y = [k(a) for a in x]

plt.xlabel('x')
plt.ylabel('k(x)')
plt.grid()

plt.scatter(x, y, color='purple')

plt.show()
```

### 函数的值域
\begin{equation}p(x) = x^{2} + 1\end{equation}

\begin{equation}\{p(x) \in \rm I\!R\;\;|\;\; p(x) \ge 1 \}\end{equation}

```python
def p(x):
    return x**2 + 1

x = np.array(range(-100, 101))

plt.xlabel('x')
plt.ylabel('p(x)')
plt.grid()

plt.plot(x, p(x), color='purple')

plt.show()
```


```python
import hublib
import pandas as pd
import ipywidgets as widgets
from IPython.display import clear_output
import matplotlib
%matplotlib notebook
import matplotlib.pyplot as plt
import scipy
from scipy.signal import savgol_filter
import numpy as np
from decimal import Decimal
import unicodedata
from unicodedata import lookup as GL
import sympy as sy
from joblib import Parallel, delayed
from lmfit import Model
import warnings
import zipfile
from zipfile import ZipFile
import os
# from hublib.ui import FileUpload, Download

from scipy import sparse
from scipy.sparse.linalg import spsolve
```

```python
### Import spectrum and do preliminary calculation here
### Output: I_raw(+ve), W

# import the file. We usually allow users to upload their own file
path = "./data/raw-fit/testing2.txt"
data = pd.read_table(path)

# calculate the number of rows and columns in the file.
# We use this to determine the format of the file and import the data accordingly
cols = data.shape[1]
rows = data.shape[0]

# import data as a DataFrame, such that the first column has the frequency and the second column has the intensity
if cols == 1:
    data = pd.Dataframe(data.iloc[0:row/2, 0], data.iloc[rows/2:rows, 0])
elif cols == 2:
    if type(data.iloc[0,0]) is str:
        data = data.iloc[1:rows, :]
    else:
        data = data
else:
    data = []

# create the frequency and intensity numpy arrays
frequency = np.array(data.iloc[:,0])
intensity = np.array(data.iloc[:,1])
length = len(frequency)

# remove all negative values from the two arrays
a = 0
for i in range(length):
    if frequency[i]<=0:
        a = a + 1
    else:
        break
frequency = frequency[a:]
intensity = intensity[a:]

# normalise the intenisty
intensity_norm = []
for i in intensity:
    intensity_norm.append((i-np.min(intensity))/(np.max(intensity)-np.min(intensity)))
```

```python
### Fit BL
### Input: I_raw, W, *args (degree, here)
### Output: I, W

# define the baseline subtraction function
def fit_BL(degree, x, y):
#     n = degree
#     I_raw = np.array(y)
#     W = np.array(x)

#     # perform baseline fitting
#     polyx = np.array([W[0],W[int(len(W)/2)],W[len(W)-1]])
#     polyy = np.array([I_raw[0],I_raw[int(len(W)/2)],I_raw[len(W)-1]])
#     bkgfit = np.polyfit(W,I_raw,degree)
#     bkgpoly = 0
#     for i in range(n):
#         bkgpoly = bkgpoly + (bkgfit[i]*W**(n-i))
#     I_raw = I_raw-bkgpoly

#     # Flatten the baseline
#     m = (I_raw[len(W)-1]-I_raw[0])/(W[len(W)-1]-W[0])
#     b = I_raw[len(W)-1]-m*W[len(W)-1]
#     bkglin = m*W+b
#     I_raw = I_raw-bkglin

#     # re-normalise the baseline subracted spectrum
#     I_BL = []
#     I_BL = ((I_raw-np.min(I_raw))/np.max(I_raw-np.min(I_raw)))

#     return I_BL

    lam = 100000
    p = 0.01
    niter=10

#     def baseline_als(y, lam, p, niter=10):
    L = len(y)
    D = sparse.diags([1,-2,1],[0,-1,-2], shape=(L,L-2))
    w = np.ones(L)
    for i in range(niter):
        W = sparse.spdiags(w, 0, L, L)
        Z = W + lam * D.dot(D.transpose())
        z = spsolve(Z, w*y)
        w = p * (y > z) + (1-p) * (y < z)
#     return z

    I_raw = y-z

    print(type(I_raw))
    print(sparse.issparse(I_raw))

    # re-normalise the baseline subracted spectrum
    I_BL = []
    I_BL = ((I_raw-np.min(I_raw))/np.max(I_raw-np.min(I_raw)))

    print(type(I_BL))
    print(sparse.issparse(I_BL))

    return I_BL
```

```python
y = intensity_norm
window_length = 7
polyorder = 2

y_smooth = savgol_filter(y, window_length, polyorder, deriv=0, delta=1.0, axis=- 1, mode='interp', cval=0.0)
```

```python
### define parameters here.
### Degree (so far, degree of baseline polynomial)

degree = 3

# call the baseline subtraction function
I_BL = fit_BL(degree, frequency, y_smooth)
```

    <class 'numpy.ndarray'>
    False
    <class 'numpy.ndarray'>
    False

```python
### Plot [I_raw vs W] & [I vs W]

fig, ax = plt.subplots(nrows=3,ncols=1, figsize=(8,12)) # create a figure with sub-plots
ax[0].plot(frequency, intensity_norm); # display the output image
ax[1].plot(frequency, y_smooth) # display the original image
ax[2].plot(frequency, I_BL) # display the original image

# label the images
ax[0].set_title('Normalised Spectrum')
ax[1].set_title('De-noised Spectrum')
ax[2].set_title('Baseline-subtracted Spectrum')
```

    <IPython.core.display.Javascript object>

    Text(0.5, 1.0, 'Baseline-subtracted Spectrum')

Other residual code:

```python
def Spectra(s,data):
    srow=0;
    if type(data[0][0])==str:
        srow=1

    W=data[0][srow:len(data)]
    W=np.array(W);W=W.astype(float)
    I_raw=data[1][srow:len(data)]
    I_raw=np.array(I_raw);I_raw=I_raw.astype(float)
    I_raw.shape=(100,)
    I_raw.shape[0]=100
    range(100)
    range(1,(I_raw.shape[0]-1))

    x = I_raw
    window_length = 15
    polyorder = 3

    I_raw = scipy.signal.savgol_filter(x, window_length, polyorder, deriv=1, delta=1.0, axis=- 1, mode='interp', cval=0.0)

#background fitting could be done, but it sometimes messes up some spectra
#in general, the hope is that the specra will not need it

#     polyx=np.array([W[0],W[int(len(W)/2)],W[len(W)-1]])
#     polyy=np.array([I_raw[0],I_raw[int(len(W)/2)],I_raw[len(W)-1]])
#     bkgfit=np.polyfit(polyx,polyy,2)
#     bkgpoly=(bkgfit[0]*W**2)+(bkgfit[1]*W)+bkgfit[2]
#     I_raw=I_raw-bkgpoly

#     m=(I_raw[len(W)-1]-I_raw[0])/(W[len(W)-1]-W[0])
#     b=I_raw[len(W)-1]-m*W[len(W)-1]
#     bkglin=m*W+b

    n=2

    polyx = np.array([W[0],W[int(len(W)/2)],W[len(W)-1]])
    polyy = np.array([I_raw[0],I_raw[int(len(W)/2)],I_raw[len(W)-1]])
    bkgfit = np.polyfit(W,I_raw,n)
    bkgpoly = 0
    for i in range(n):
        bkgpoly = bkgpoly + (bkgfit[i]*W**(n-i))
    I_raw = I_raw-bkgpoly

    m = (I_raw[len(W)-1]-I_raw[0])/(W[len(W)-1]-W[0])
    b = I_raw[len(W)-1]-m*W[len(W)-1]
    bkglin = m*W+b

    I_raw=I_raw-bkglin

    I=((I_raw-np.min(I_raw))/np.max(I_raw-np.min(I_raw)));

    s.I=I

    s.W=W
    return s
```