Metadata-Version: 2.4
Name: mason-solver
Version: 0.1.1
Summary: Symbolic Mason Gain Formula Solver
Requires-Python: >=3.8
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: sympy
Requires-Dist: networkx
Requires-Dist: pytest
Requires-Dist: control
Requires-Dist: streamlit
Requires-Dist: ipython
Dynamic: license-file

![Python](https://img.shields.io/badge/python-3.10+-blue)
![License](https://img.shields.io/badge/license-MIT-green)
# Mason Solver

> Symbolic Mason Gain Formula Solver for Control Systems
> 基于符号计算的信号流图传递函数求解工具

---

## 📌 项目简介

本项目实现了 **Mason 增益公式（Mason's Gain Formula）** 的自动化求解，支持：

* 单输入单输出（SISO）系统
* 多输入多输出（MIMO）系统
* 符号表达（基于 `sympy`）
* 信号流图建模
* 自动路径、回路与系统行列式计算
* 传递矩阵生成

适用于：

* 自动控制原理课程
* 控制系统建模与分析
* 教学与验证工具
* 符号推导与科研辅助

---

## ⚙️ 安装方式

### 克隆代码
```bash
git clone https://github.com/Meeta-factor/mason.git
cd mason
```
### 安装
#### 虚拟环境安装
```bash
python -m venv .venv
source .venv/bin/activate
pip install -e .
```
#### 本地安装
```bash
pip install .
```


---

## 🚀 快速开始

### 1️⃣ 构建系统

```python
from mason.solver import MasonSolver,MIMOSFGSolver,ShannonHappSolver
solver = MIMOSFGSolver(MasonSolver)
data = {
    "edges": [
        ("R1", "C1", "G11"),
        ("R1", "C2", "G12"),
        ("R2", "C1", "G21"),
        ("R2", "C2", "G22"),
    ],
    "sources": ["R1", "R2"],
    "sinks": ["C1", "C2"],
}
solver.load_from_dict(data)
```

---

### 2️⃣ 计算传递矩阵

```python
G,info = solver.transfer_matrix(
    sources=data["sources"],
    sinks=data["sinks"]
)

display(G)
```

输出：

```
Matrix([
[G11, G21],
[G12, G22]
])
```

---

### 3️⃣ 数学含义

该矩阵满足：

$$
\mathbf{y} = G(s)\mathbf{u}
$$

其中：

* 行 → 输出（sinks）
* 列 → 输入（sources）
* $G_{ij}$ 表示：第 j 个输入到第 i 个输出的传递函数

---

### 4️⃣ 查看详细推导过程

```python
from mason.visualize import show_result
show_result(info,entry=("C1","R2"))
```

展示内容包括：

* Forward Paths（前向通路）
* Loops（回路）
* $\Delta$（系统行列式）
* $\Delta_k$（非接触回路修正项）

---

## 🎉 Examples

- `examples/solver.ipynb` – basic usage
- `examples/control.ipynb` – control interface
- `examples/load.ipynb` – classic control example
- `examples/loop3.ipynb` – multi-loops example
- `examples/shannon.ipynb` – shannon example
---

## 📊 功能特性

* ✅ 自动枚举前向路径
* ✅ 自动检测回路与非接触回路
* ✅ 符号计算支持（SymPy）
* ✅ 支持复杂反馈结构
* ✅ MIMO 传递矩阵



---



## 📁 项目结构

```
mason/
├── solver.py        # 核心算法
├── visualize.py     # 可视化与结果展示
├── typing_defs.py   # 类型定义
examples/
├── control.ipynb
├── load.ipynb
├── shannon.ipynb
├── solver.ipynb
```

---

## 🧠 理论基础

### **Mason 增益公式**

$$T = \frac{\sum_{k} P_{k} \Delta_{k}}{\Delta}$$


其中：

*  $P_k $：第 k 条前向路径
*  $\Delta$：系统行列式
*  $\Delta_k$ ：与路径不接触的回路组成的行列式
### **Shannon happ公式**
本项目除了支持经典的 Mason 增益公式外，也支持使用 **Shannon–Happ 公式** 计算信号流图的传递函数。
Shannon–Happ 公式是求解信号流图传递函数的另一种经典方法。  
它的基本思想是：在原始开环信号流图的基础上，从输出节点到输入节点人为添加一条增益为 C 的支路，其中 $G$ 为待求传递函数。这样，原来的开环图就被转化为一个闭合图。
在这个闭合图上，传递函数的求解可以转化为对系统中各类回路及其互不接触组合的分析，而不再需要像 Mason 公式那样显式列出前向通路及对应的余子式。

其特征方程通常可以写成：

$$\frac{1}{G}=1-\sum L_i+\sum L_iL_j-\sum L_iL_jL_k+\cdots=0$$

其中：

- $L_i$ 表示单个回路的增益；
- $L_iL_j$ 表示两个互不接触回路的增益乘积；
- $L_iL_jL_k$ 表示三个两两互不接触回路的增益乘积；
- 更高阶项以此类推。

通过求解上述关于 $\frac{1}{G}$ 的方程，即可得到系统的传递函数 $G$。

---

## 🎉TIKZ实现初步的信号流图
### 前提条件:texlive-extra安装
### SISO系统
![loop3](./mason/tikz/loop3.png)
### MIMO+自耦+互耦
![ex](./mason/tikz/ex.png)
![data](./mason/tikz/data.png)




---

## 📌 适用方向

* 自动控制原理
* 信号与系统
* 控制系统建模
* 最优控制（预处理工具）
* 符号推导验证

---

## 🧩 未来计划

* [x] 状态空间转换
* [ ] 自动生成报告（LaTeX）
* [ ] 控制系统解耦分析
* [ ] LQR / 最优控制接口

---

## 👤 作者

* Meta(Meeta-factor)（Control Engineering Student）

---

## 📜 License

This project is licensed under the MIT License.

---

## 📖 数据格式与 API

信号流图使用字典描述，其中每条边均为 `(起点, 终点, 增益)`。增益可以是
`SymPy` 表达式，也可以是能够被 `sympy.sympify` 解析的字符串，例如
`"G1"`、`"-H"`、`"1/(s+1)"` 或 `"G1*G2"`。

### SISO 输入格式

```python
data = {
    "edges": [
        ("R", "x", "G"),
        ("x", "C", "1/(s+1)"),
        ("C", "x", "-H"),
    ],
    "source": "R",
    "sink": "C",
}
```

使用 Mason 公式求解：

```python
from mason.solver import MasonSolver

solver = MasonSolver()
solver.load_from_dict(data)
T, info = solver.solve()

print(T)  # G/(H + s + 1)
```

也可以不预先设置输入、输出节点，直接计算任意两节点之间的传递函数：

```python
T, info = solver.transfer_function("R", "C", expand_result=True)
```

`expand_result=True` 会展开最终的符号表达式。对于包含扰动节点的图，可使用：

```python
Td, info = solver.disturbance_transfer_function("D", "C")
```

### MIMO 输入格式

MIMO 系统以输出为行、输入为列构成传递矩阵。`info["entry_info"]` 保存了
每个 `(sink, source)` 元素的完整 Mason 推导信息。

```python
from mason.solver import MasonSolver, MIMOSFGSolver

solver = MIMOSFGSolver(MasonSolver)
solver.load_from_dict({
    "edges": [
        ("R1", "C1", "G11"),
        ("R1", "C2", "G12"),
        ("R2", "C1", "G21"),
        ("R2", "C2", "G22"),
    ],
    "sources": ["R1", "R2"],
    "sinks": ["C1", "C2"],
})

G, info = solver.solve()
G_c1_r2 = info["entry_info"][("C1", "R2")]["TransferFunction"]
```

### Shannon-Happ 求解

`ShannonHappSolver` 会临时添加一条从输出回到输入、增益为 `1/T` 的支路，
构造特征方程后对 `T` 进行符号求解。其输入格式与 SISO Mason 相同。

```python
from mason.solver import ShannonHappSolver

solver = ShannonHappSolver()
solver.load_from_dict(data)
T, info = solver.solve(T_symbol="T")
```

如需用 Shannon-Happ 方法逐元素计算 MIMO 矩阵，可将其作为 MIMO 包装器的后端：

```python
solver = MIMOSFGSolver(ShannonHappSolver)
```

---

## 🔍 结果展示

求解方法均返回 `(result, info)`。`info` 包含前向通路、回路、非接触回路组合、
系统行列式和最终传递函数，可在 Jupyter Notebook 中用 `show_result` 展示：

```python
from mason.visualize import show_result

show_result(info)                 # SISO Mason 或 Shannon-Happ
show_result(info, entry=("C1", "R2"))  # MIMO 的指定矩阵元素
```

MIMO 的 `entry` 也支持从零开始的矩阵索引，例如 `entry=(0, 1)`。

---

## 🔄 转换为 python-control 模型

`mason.adapters.control` 可将只含拉普拉斯变量 `s` 的数值化 SymPy 传递矩阵转换为
`python-control` 的传递函数或状态空间模型。符号参数必须通过 `subs_dict` 全部替换。

```python
import sympy as sp
from mason.adapters.control import matrix_to_control_ss

s = sp.Symbol("s")
Gsym = sp.Matrix([[10 / (s + 2)]])
sys = matrix_to_control_ss(Gsym, s, minimal=True)

A, B, C, D = sys.A, sys.B, sys.C, sys.D
```

可使用 `matrix_to_control_tf` 获得 `python-control` 传递函数对象，或使用
`matrix_to_ss_matrices` 直接获得 `(A, B, C, D)` 矩阵。

---

## 🌐 Web 界面

项目内置 Streamlit 页面，支持手动输入图数据或上传边列表 CSV，运行：

```bash
streamlit run app.py
```

CSV 至少需要起点、终点与增益三列。列名可使用以下任一种组合：

```csv
start,end,gain
R,x1,G1
x1,C,G2
```

起点列也可命名为 `from` 或 `u`，终点列也可命名为 `to` 或 `v`，增益列也可命名为
`G` 或 `weight`。SISO 模式需额外指定 `source` 与 `sink`；MIMO 模式需指定
`sources` 与 `sinks`。

---

## 🖼️ 从 CSV 生成 TikZ 图

`mason/tikz/mason_build.py` 能将 `start,end,gain` 格式的 CSV 转为独立的 TikZ/LaTeX
文档，并按常见的主通道、反馈、交叉耦合和双支路命名自动布局：

```bash
python mason/tikz/mason_build.py mason/tikz/loop3.csv
pdflatex mason/tikz/loop3.tex
```

可指定输出文件：

```bash
python mason/tikz/mason_build.py input.csv output.tex
```

生成 PDF 需要可用的 LaTeX 环境，以及包含 TikZ 的 `texlive-extra`。

---

## ⚠️ 使用限制

* 图内部使用 `networkx.DiGraph` 表示，同一对节点只能保留一条边；重复添加会覆盖原增益。
* 若输入到输出之间不存在前向通路，求解器会抛出 `ValueError`。
* Shannon-Happ 方法要求原图中不存在 `sink -> source` 的边，否则临时闭环边会与其冲突。
* 回路与互不接触回路组合通过枚举获得，节点和回路较多时计算量会快速增长，适合教学、验证和中小规模的符号分析。
