向正无穷舍入
Y = ceil(t) 将 t 的每个元素四舍五入到大于或等于此元素的最接近的数.
t是标量,向量,矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def ceil_positive_infinity(input_str):
"""
对输入进行向上取整操作,支持数值、符号表达式和矩阵。
参数:
input_str (str): 输入的字符串,可以是数值、符号表达式或矩阵。
返回:
result (sp.Expr, sp.Matrix, or str):
- 若输入为数值或符号表达式,返回向上取整后的表达式;
- 若输入为矩阵,返回逐元素向上取整后的矩阵;
- 若输入无效,返回错误消息。
"""
try:
# 修复输入表达式(例如替换特殊符号)
# 将字符串转换为 SymPy 表达式
expr = sp.sympify(input_str)
error = False
result = None
# 检查输入
if expr.free_symbols:
# 处理含自由符号的表达式
result = sp.ceiling(expr)
elif expr.is_number:
# 处理数值
z = float(expr)
result = np.ceil(z)
else:
error = True
if error:
return f"输入错误: {input_str}"
else:
return result
except Exception as e:
return f"错误: {e}"
def main():
"""
主函数,用于演示 ceil_positive_infinity 函数的使用。
"""
# 示例输入
test_cases = [
"3.2", # 4.0
"-4.7", # -4.0
"x", # ceiling(x)
"x + 0.5", # ceiling(x + 0.5)
"oo", # inf
]
# 遍历测试用例并输出结果
for case in test_cases:
output = ceil_positive_infinity(case)
print(f"输入: {case}")
print(f"输出: {output}")
print("-" * 40)
if __name__ == "__main__":
main()
分解连分数
s = cFrac(n).
连分数是一种特殊的分数表示方法它可以用一系列的有理数来表示.这些有理数被称为连分数的部分,它们描述了数的分数部分.
n是浮点数
s是由有理数组成的连分数.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from sympy.ntheory.continued_fraction import continued_fraction
def continue_fraction_rational(input_str):
"""
计算有理数的连分数展开式。
参数:
input_str (str): 输入的字符串,表示一个有理数(如整数、分数或有限小数)。
返回:
result (list or str):
- 若输入有效,返回连分数展开式的系数列表;
- 若输入无效,返回错误消息。
错误处理:
- 输入为非数值(如矩阵、符号表达式)时返回输入错误。
- 输入为无理数或无法转换为有理数的值时返回错误。
"""
try:
# 将输入字符串转换为 SymPy 表达式
expr = sp.sympify(input_str)
error = False
result = None
# 检查输入是否为元组(不支持元组输入)
if isinstance(expr, tuple):
error = True
# 检查输入是否为数值类型(整数、有理数、浮点数)
elif expr.is_number:
# 将输入转换为精确有理数(例如 3.2 → 16/5)
rational_num = sp.Rational(expr)
# 计算连分数展开式
result = list(continued_fraction(rational_num))
else:
error = True
if error:
return f"输入错误: {input_str}"
else:
return result
except Exception as e:
return f"错误: {e}"
def main():
"""
主函数,用于演示 `continue_fraction_rational` 函数的使用。
"""
# 示例输入
test_cases = [
"3/2", # [1, 2]
"5", # [5]
"2.5", # [2, 2]
"0.3333", # [0, 3, 3332, 1, 674191559, 1, 61, 7, 6]
]
# 遍历测试用例并输出结果
for case in test_cases:
output = continue_fraction_rational(case)
print(f"输入: {case}")
print(f"输出: {output}")
print("-" * 40)
if __name__ == "__main__":
main()
置换积分
G=changeIntegrationVariable(F,old,new)通过替换对F中的积分进行积分,其中old被new替换.
旧的必须依赖于F中积分的前一个积分变量,新的必须依赖新的积分变量.
在F中指定积分时,您可以通过使用int函数并将“Hold”选项设置为true来返回未求值的积分形式. 然后,您可以使用changeIntegrationVariable显示通过替换进行集成的步骤.
F —— 包含积分的表达式, 表达式向量, 表达式矩阵
old--要替换的子表达式
new--新的子表达式
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
from sympy import Integral, solve, diff, symbols, Function
from sympy.core.basic import Basic
import sympy as sp
def change_integration_variable(F, old, new):
"""
将积分中的变量替换应用于表达式 \( F \),用新变量替换旧变量。
返回变换后的表达式。
"""
def replace_integral(expr, old, new):
if isinstance(expr, Integral):
integrand = expr.function
limits = list(expr.limits)
substituted = False
for i in range(len(limits)):
if substituted:
break
limit = limits[i]
var = limit[0] # 积分变量(如x)
a = limit[1] if len(limit) > 1 else None # 下限
b = limit[2] if len(limit) > 2 else None # 上限
# 只处理包含旧变量的积分变量
if not old.has(var):
continue
# 提取新变量t(如t必须是新引入的符号)
t = new.free_symbols - old.free_symbols
if len(t) != 1:
raise ValueError("必须指定一个新变量")
t = t.pop()
# 步骤1:解方程 old = new 得到 var = g(t)
solutions = solve(old - new, var)
if not solutions:
raise ValueError(f"无法解方程 {old} = {new}")
# 步骤2:计算新积分限(用old的表达式在原始积分限处的值)
t_a_val = old.subs(var, a) if a is not None else None
t_b_val = old.subs(var, b) if b is not None else None
# 步骤3:验证解是否满足原始积分限
valid_solution = None
for sol in solutions:
# 检查当t等于新积分限时,解是否还原回原始积分限
valid_a = True
valid_b = True
if t_a_val is not None:
x_at_ta = sol.subs(t, t_a_val)
valid_a = x_at_ta.equals(a)
if t_b_val is not None:
x_at_tb = sol.subs(t, t_b_val)
valid_b = x_at_tb.equals(b)
if valid_a and valid_b:
valid_solution = sol
break
if not valid_solution:
raise ValueError("无法找到满足积分限的解")
# 步骤4:计算雅可比行列式并替换变量
dvar_dt = diff(valid_solution, t)
new_integrand = integrand.subs(var, valid_solution) * dvar_dt
# 构造新积分限
new_limits = [(t, t_a_val, t_b_val) if a is not None and b is not None else (t,)]
substituted = True
# 替换积分并返回
return Integral(new_integrand, *new_limits)
elif isinstance(expr, Basic):
return expr.func(*[replace_integral(arg) for arg in expr.args])
else:
return expr
return replace_integral(F, old, new)
x, a, b, c, t = symbols('x a b c t')
f = Function('f')(x + c)
F = Integral(f, (x, a, b))
G = change_integration_variable(F, x + c, t)
print(G)
# Integral(f(t), (t, a + c, b + c))
F = Integral(x ** 2, (x, 0, 1))
G = change_integration_variable(F, x ** 2, t)
print(G)
# Integral(sqrt(t)/2, (t, 0, 1))
f = Function('f')(sp.exp(sp.sqrt(sp.sin(x))))
F = Integral(f, (x, 0, 1))
G = change_integration_variable(F, sp.sqrt(sp.sin(x)), t)
print(G)
# Integral(2*t*f(exp(sqrt(t**2)))/sqrt(1 - t**4), (t, 0, sqrt(sin(1))))
字符的ASCII数字值
Y = char(Z) 如果Z是字符,转成相应的ASCII数字值. 如果Z是数字, 转成相应的字符.
Z是标量
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
def char_to_ascii(input_str):
"""
将字符转换为 ASCII 码或将 ASCII 码转换为字符。
参数:
input_str (str): 输入的字符串,可以是字符、ASCII 码或符号表达式。
返回:
res (int, str, or str):
- 若输入为字符,返回其 ASCII 码;
- 若输入为 ASCII 码,返回对应的字符;
- 若输入为符号表达式,返回其字符串形式的 ASCII 码;
- 若输入无效,返回错误消息。
"""
try:
# 将输入字符串转换为 SymPy 表达式
expr = sp.sympify(input_str)
error = False
res = None
# 检查输入是否为数值类型(ASCII 码)
if expr.is_integer:
# 将数值转换为字符
res = chr(int(expr))
# 检查输入是否为符号表达式
elif expr.free_symbols:
# 将符号表达式转换为字符串并取第一个字符的 ASCII 码
res = ord(str(expr)[0])
else:
error = True
if error:
return f"输入错误: {input_str} 必须是单个字符或 ASCII 码。"
else:
return res
except Exception as e:
return f"错误: {e}"
def main():
"""
主函数,用于演示 `char_to_ascii` 函数的使用。
"""
# 示例输入
test_cases = [
"A", # 65
"65", # A
"x", # 120
"Hello", # 72
]
# 遍历测试用例并输出结果
for case in test_cases:
output = char_to_ascii(case)
print(f"输入: {case}")
print(f"输出: {output}")
print("-" * 40)
if __name__ == "__main__":
main()
切比雪夫谱微分矩阵
A = chebspec(n,k) 返回一个大小为 n×n 的切比雪夫谱微分矩阵. 参量 k 可以取值 0(默认值)或 1,它决定输出矩阵的字符.
对于 k = 0(无边界条件), A 是幂零矩阵, 这意味着存在满足 A^c = 0 的正整数 c, 矩阵 A 具有空向量 ones(n,1).
对于 k = 1, A 是非奇异且条件设置良好的矩阵, 其特征值具有负实部
n,k - 输入, 标量
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def chebspec_matrix(input_str):
"""
生成Chebyshev谱微分矩阵。输入应为字符串形式,如"3"(一阶3阶矩阵)或"(4,2)"(二阶4阶矩阵)。
参数:
input_str: 字符串形式的输入,如"3"或"(4,2)"。
返回:
SymPy矩阵对象或错误信息字符串。
"""
try:
expr = sp.sympify(input_str)
error = False
result = None
def eval_chebspec_matrix(n, k=1):
"""内部函数:计算n阶k次导数的Chebyshev微分矩阵。"""
# 生成Chebyshev节点(在区间[-1,1]上的极值点)
x = np.cos(np.pi * np.arange(n) / (n - 1))
# 初始化微分矩阵
D = np.zeros((n, n))
c = np.ones(n)
c[0], c[-1] = 2, 2 # 首尾节点缩放因子
# 填充非对角线元素
for i in range(n):
for j in range(n):
if i != j:
D[i, j] = (c[i] / c[j]) * (-1) ** (i + j) / (x[i] - x[j])
# 对角线元素为行和的相反数
D[i, i] = -np.sum(D[i, :])
# 计算k次导数矩阵(矩阵的k次幂)
return np.linalg.matrix_power(D, k) if k > 1 else D
# 解析输入参数:支持格式如 "3" 或 "(4, 2)"
if isinstance(expr, tuple) and len(expr) == 2:
if all(e.is_number for e in expr):
params = tuple(int(e.evalf()) for e in expr)
result = eval_chebspec_matrix(*params)
else:
error = True
elif expr.is_number:
result = eval_chebspec_matrix(n=int(expr))
else:
error = True
return sp.Matrix(result) if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
if __name__ == "__main__":
# 示例1:生成3阶一阶微分矩阵
print("示例1:3阶Chebyshev微分矩阵:")
print(chebspec_matrix("3"))
# Matrix([[1.50000000000000, -2.00000000000000, 0.500000000000000],
# [0.500000000000000, -1.11022302462516e-16, -0.500000000000000],
# [-0.500000000000000, 2.00000000000000, -1.50000000000000]])
# 示例2:生成4阶二阶微分矩阵
print("\n示例2:4阶二阶Chebyshev微分矩阵:")
print(chebspec_matrix("(4,2)"))
# Matrix([[5.33333333333334, -9.33333333333334, 6.66666666666667, -2.66666666666667],
# [3.33333333333333, -5.33333333333334, 2.66666666666667, -0.666666666666666],
# [-0.666666666666666, 2.66666666666667, -5.33333333333333, 3.33333333333333],
# [-2.66666666666667, 6.66666666666666, -9.33333333333333, 5.33333333333333]])
切比雪夫多项式的类范德蒙类矩阵
A = chebvand(x) 基于由点 x 组成的向量生成原始切比雪夫范德蒙矩阵, 这些点定义计算切比雪夫多项式的位置. 参量x是长度为 n 的向量,
A 的大小为 n×n. A 中的项满足 A(i,j) = Ti – 1(x(j)), 其中 Ti – 1 是 i - 1 次第一类切比雪夫多项式. 如果 x 为标量,则将使用区间 [0,1] 上的 x 个等间距点计算A
x - 输入, 向量
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import numpy as np
import sympy as sp
def chebvand_matrix(input_str):
"""
生成Chebyshev-Vandermonde矩阵。
参数:
input_str: 输入的字符串,表示节点列表(例如 "[0, 1, 2]")。
返回:
如果输入有效,返回对应的SymPy矩阵对象;否则返回错误信息。
"""
try:
# 预处理输入字符串,替换常见中文符号
input_str = input_str.strip().replace(',', ',').replace('【', '[').replace('】', ']')
expr = sp.sympify(input_str)
error = False
result = None
def evaluation_chebvand_matrix(x):
"""
根据节点x生成Chebyshev-Vandermonde矩阵。
参数:
x: 节点列表(NumPy数组)。
返回:
Chebyshev-Vandermonde矩阵(NumPy数组)。
"""
n = len(x)
V = np.zeros((n, n))
# 用Chebyshev多项式T_j(x_i)填充矩阵
for i in range(n):
for j in range(n):
V[i, j] = np.cos(j * np.arccos(x[i]))
return V
if isinstance(expr, tuple):
error = True
elif isinstance(expr, list):
x = np.array(expr, dtype=float)
result = evaluation_chebvand_matrix(x=x)
result = sp.Matrix(result)
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
if __name__ == "__main__":
# 定义测试用例
test_cases = [
"[0.5, 0, -0.5]",
# Matrix([[1.00000000000000, 0.500000000000000, -0.500000000000000],
# [1.00000000000000, 6.12323399573677e-17, -1.00000000000000],
# [1.00000000000000, -0.500000000000000, -0.500000000000000]])
"[1, 0.5, 0]",
# Matrix([[1.00000000000000, 1.00000000000000, 1.00000000000000],
# [1.00000000000000, 0.500000000000000, -0.500000000000000],
# [1.00000000000000, 6.12323399573677e-17, -1.00000000000000]])
"[0, 1, 2]",
# Matrix([[1.00000000000000, 6.12323399573677e-17, -1.00000000000000],
# [1.00000000000000, 1.00000000000000, 1.00000000000000],
# [nan, nan, nan]])
]
# 遍历测试用例
for case in test_cases:
print(f"测试输入:{case}")
matrix = chebvand_matrix(case)
print("结果:")
if isinstance(matrix, sp.Matrix):
print(matrix) # 使用SymPy的漂亮打印输出矩阵
else:
print(matrix)
print("\n" + "=" * 50 + "\n")
切比雪夫窗
w = chebwin(L,at,sym=1) 返回一个长度为L个点, 衰减为at的修正的矩形窗 默认sym=1
当sym=1, 生成一个对称窗口,用于滤波器设计.
当sym=0, 生成一个周期性窗口,用于光谱分析.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from scipy import signal
def chebyshev_window(input_str):
"""
根据输入的参数生成切比雪夫窗口系数。
参数:
input_str (str): 格式为'(m, at)'或'(m, at, sym)'的字符串,其中
- m (int): 窗口长度(必须为正整数)
- at (float): 主瓣衰减系数(单位:分贝)
- sym (int, 可选): 对称性标志(0表示非对称,1表示对称,默认为1)
返回:
list | str: 成功返回窗口系数列表,失败返回错误描述字符串
"""
try:
# 将输入字符串解析为SymPy表达式
expr = sp.sympify(input_str)
# 检查是否为元组格式输入
if not isinstance(expr, tuple):
return f"输入格式错误:需为元组格式,如'(11, 50)'"
# 参数数量检查
if len(expr) < 2:
return "参数不足:至少需要窗口长度和衰减系数两个参数"
# 解析基础参数
m = int(expr[0])
at = float(expr[1])
# 处理对称性参数(默认对称)
sym = True
if len(expr) >= 3:
if expr[2] == 0: # 第三个参数为0时设为非对称
sym = False
# 参数有效性检查
if m <= 0:
return "窗口长度必须为正整数"
if at <= 0:
return "衰减系数必须为正数"
# 生成切比雪夫窗口
window = signal.windows.chebwin(m, at, sym)
return list(window)
except Exception as e:
return f"处理过程中发生错误:{str(e)}"
if __name__ == "__main__":
# 测试用例
test_cases = [
"(7, 50)",
# 前5个系数:[0.11169109836363081, 0.419629989244334, 0.8137735925687217, 1.0, 0.8137735925687217]
"(8, 40.5, 0)",
# 前5个系数:[0.1261675884188586, 0.3449958474928207, 0.639797528234691, 0.897289854502741, 1.0]
"(9, 60, 1)",
# 前5个系数:[0.05186856359432399, 0.22712393362332237, 0.5379172015600897, 0.8604844373949189, 1.0]
"(5, 50, 3)",
# [0.20549421633071246, 0.70104634453696, 1.0, 0.70104634453696, 0.20549421633071246]
]
# 执行测试
for case in test_cases:
print(f"输入:{case}")
result = chebyshev_window(case)
if isinstance(result, list):
print(f"生成成功!窗口长度:{len(result)}")
print(f"前5个系数:{result[:5]}") if len(result) >= 5 else print(f"系数:{result}")
else:
print(f"错误信息:{result}")
第一类切比雪夫多项式
ChebyshevT(n,x)表示在点x处的第一类第n次Chebyshev多项式
n是多项式的次数, 标量,向量,数组,矩阵.
x是评估点,标量,向量,数组,矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from scipy.special import eval_chebyt
def chebyshevt_polynomial(input_str):
"""
计算切比雪夫多项式,支持标量和矩阵输入
参数:
input_str (str): 输入表达式字符串,格式为"(n, x)",其中
n: 多项式阶数(整数或整数矩阵)
x: 变量值或变量矩阵
返回:
sp.Expr 或 sp.Matrix 或 str: 计算结果,错误时返回错误描述字符串
功能说明:
1. 支持标量计算:如输入"(3, 0.5)"返回T3(0.5)的值
2. 支持矩阵计算:当n或x为矩阵时,进行逐元素计算
3. 输入验证:检查阶数有效性、矩阵形状匹配等
"""
try:
# 符号化输入表达式
expr = sp.sympify(input_str)
error = False
result = None
# 输入验证
if isinstance(expr, tuple) and len(expr) == 2:
"""计算单个元素的切比雪夫多项式值"""
if all(e.is_number for e in expr):
n, x = expr
n_raw = float(n)
x_raw = complex(x)
result = eval_chebyt(n_raw, x_raw)
elif any(e.free_symbols for e in expr):
result = sp.expand_func(sp.chebyshevt(*expr))
else:
error = True
else:
error = True
return result if not error else f"输入错误:{input_str}"
except Exception as e:
return f"计算错误:{str(e)}"
if __name__ == "__main__":
# 测试用例
test_cases = [
"(3, 0.5)", # (-1+0j)
"(4,x)", # 8*x**4 - 8*x**2 + 1
]
# 执行测试
for case in test_cases:
print(f"输入:{case}")
result = chebyshevt_polynomial(case)
if isinstance(result, (sp.Expr, sp.Matrix)):
print("计算结果:")
print(result)
else:
print(f"错误信息:{result}")
print("-" * 60)
第二类切比雪夫多项式
ChebyshevU(n,x)表示在点x处的第二类第n次Chebyshev多项式
n是多项式的次数, 标量,向量,数组,矩阵.
x是评估点,标量,向量,数组,矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from scipy.special import eval_chebyu
def chebyshevu_polynomial(input_str):
"""
计算切比雪夫多项式,支持标量和矩阵输入
参数:
input_str (str): 输入表达式字符串,格式为"(n, x)",其中
n: 多项式阶数(整数或整数矩阵)
x: 变量值或变量矩阵
返回:
sp.Expr 或 sp.Matrix 或 str: 计算结果,错误时返回错误描述字符串
功能说明:
1. 支持标量计算:如输入"(3, 0.5)"返回T3(0.5)的值
2. 支持矩阵计算:当n或x为矩阵时,进行逐元素计算
3. 输入验证:检查阶数有效性、矩阵形状匹配等
"""
try:
# 符号化输入表达式
expr = sp.sympify(input_str)
error = False
result = None
# 输入验证
if isinstance(expr, tuple) and len(expr) == 2:
"""计算单个元素的切比雪夫多项式值"""
if all(e.is_number for e in expr):
n, x = expr
n_raw = float(n)
x_raw = complex(x)
result = eval_chebyu(n_raw, x_raw)
elif any(e.free_symbols for e in expr):
result = sp.expand_func(sp.chebyshevu(*expr))
else:
error = True
else:
error = True
return result if not error else f"输入错误:{input_str}"
except Exception as e:
return f"计算错误:{str(e)}"
if __name__ == "__main__":
# 测试用例
test_cases = [
"(3, 0.5)", # (-1+0j)
"(4,x)", # 16*x**4 - 12*x**2 + 1
]
# 执行测试
for case in test_cases:
print(f"输入:{case}")
result = chebyshevu_polynomial(case)
if isinstance(result, (sp.Expr, sp.Matrix)):
print("计算结果:")
print(result)
else:
print(f"错误信息:{result}")
print("-" * 60)
符号表达的子表达或术语
subexpr = children(expr)返回一个无值单元格数组,其中包含符号表达式expr的子表达式.例如,求和的子表达式就是它的项.
subexr = children(A)返回一个嵌套单元格数组,其中包含符号矩阵A中每个表达式的子表达式.
expr —— 输入表达式,符号数,符号变量,符号函数,符号表达式
A —— 输入矩阵,符号矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
def child_symbolic_expression(input_str):
"""
处理符号表达式或矩阵,返回其子表达式
参数:
input_str: 输入字符串,可以是矩阵或符号表达式
返回:
子表达式结构 或 错误信息字符串
处理逻辑:
1. 尝试将输入字符串转换为SymPy表达式
2. 如果是矩阵,递归处理每个元素
3. 如果是符号表达式,提取其子表达式
4. 数值表达式返回错误信息
"""
try:
expr = sp.sympify(input_str, evaluate=False)
error = False
result = None
# 普通符号表达式处理
if expr.free_symbols:
result = expr.args
# 数值表达式或无法处理的情况
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误:{e}"
def main():
"""测试用例主函数"""
# 测试: 普通符号表达式
print("测试: 普通符号表达式")
input_str = "x + sin(y)*z"
print("输入字符串:", input_str)
print("解析结果:", child_symbolic_expression(input_str), "\n")
# 解析结果: (x, z*sin(y))
if __name__ == "__main__":
main()
卡方分布的累积分布函数
p=ChiSquareCDF(x,k)返回具有自由度k的卡方分布的累积分布函数(cdf),以x中的值进行评估.
x是评估cdf的值, 非负标量,非负标量数组.
k是自由度,正标量值,正标量值数组.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from sympy.stats import ChiSquared, cdf
from scipy.stats import chi2
def chi_squared_cdf(input_str):
"""
计算卡方分布的累积分布函数 (CDF)
参数:
input_str: 输入字符串,格式应为包含x值和自由度k的元组,例如 "(x, 2)" 或 "([1,2], 3)"
返回:
CDF计算结果 (数值/矩阵) 或 错误信息字符串
处理逻辑:
1. 将输入字符串转换为SymPy表达式
2. 解析出x值(标量/矩阵)和自由度k
3. 对每个x值计算Chi-Squared(k)的CDF
"""
try:
# 将输入字符串转换为SymPy表达式
expr = sp.sympify(input_str)
error = False
result = None
# 检查输入是否为元组 (x, k)
if isinstance(expr, tuple) and len(expr) == 2:
if all(e.is_number for e in expr):
# 验证k是否为正整数
if not (expr[1].is_Integer and expr[1] > 0):
return f"错误: 自由度k必须为正整数,当前k={expr[1]}"
"""用SciPy计算卡方分布在标量x处的CDF值"""
result = chi2.cdf(float(expr[0]), df=int(expr[1]))
elif any(e.free_symbols for e in expr):
"""计算单个值的卡方分布CDF"""
# 创建卡方分布对象
chi_dist = ChiSquared('Chi', expr[1])
# 计算CDF并转换为浮点数
result = cdf(chi_dist)(expr[0])
else:
error = True
else:
error = True
return result if not error else f"输入格式错误: 需要(x, k)元组,当前输入{input_str}"
except Exception as e:
return f"错误:{e}"
def main():
"""测试用例主函数"""
# 测试1: 标量数值输入
print("测试1: 标量数值输入")
print(chi_squared_cdf("(2, 3)")) # 应输出数值结果
# 0.42759329552912023
print(chi_squared_cdf("(5.5, 2)"), "\n") # 应输出数值结果
# 0.9360721387932924
# 测试2: 符号输入
print("测试3: 符号输入")
x = sp.symbols('x')
print(chi_squared_cdf(f"({x}, 3)"), "\n") # 应输出符号表达式
# Piecewise((-sqrt(2)*sqrt(x)*exp(-x/2)/sqrt(pi) + erf(sqrt(2)*sqrt(x)/2), x >= 0), (0, True))
if __name__ == "__main__":
main()
卡方分布的概率密度函数
y=ChiSquarePDF(x,k)返回具有k个自由度的卡方分布的概率密度函数(pdf),以x中的值进行评估.
x是评估pdf的值,非负标量,非负标量数组
k是自由度,正标量值,正标量值数组
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from sympy.stats import ChiSquared, density
from scipy.stats import chi2
def chi_squared_pdf(input_str):
"""
计算卡方分布的概率密度函数 (PDF)
参数:
input_str: 输入字符串,格式应为包含x值和自由度k的元组,例如 "(x, 2)" 或 "([1,2], 3)"
返回:
PDF计算结果 (数值/矩阵/符号表达式) 或 错误信息字符串
处理逻辑:
1. 将输入字符串转换为SymPy表达式
2. 解析出x值(标量/矩阵)和自由度k
3. 对每个x值计算Chi-Squared(k)的PDF
"""
try:
# 将输入字符串转换为SymPy表达式
expr = sp.sympify(input_str)
error = False
result = None
# 检查输入是否为元组 (x, k)
if isinstance(expr, tuple) and len(expr) == 2:
if all(e.is_number for e in expr):
# 验证k是否为正整数
if not (expr[1].is_integer and expr[1] > 0):
return f"错误: 自由度k必须为正整数,当前k={expr[1]}"
"""用SciPy计算卡方分布在标量x处的PDF值"""
result = chi2.pdf(float(expr[0]), df=int(expr[1]))
elif any(e.free_symbols for e in expr):
"""计算单个值的卡方分布PDF"""
# 创建卡方分布对象
chi_dist = ChiSquared('Chi', expr[1])
# 计算PDF并转换为浮点数或符号表达式
result = density(chi_dist)(expr[0])
else:
error = True
else:
error = True
return result if not error else f"输入格式错误: 需要(x, k)元组,当前输入{input_str}"
except Exception as e:
return f"错误:{e}"
def main():
"""测试用例主函数"""
# 测试1: 标量数值输入
print("测试1: 标量数值输入")
print(chi_squared_pdf("(2, 3)"))
# 0.2075537487102974
print(chi_squared_pdf("(5.5, 2)"), "\n") # 应输出0.026995
# 0.031963930603353785
# 测试2: 符号输入
print("测试3: 符号输入")
x = sp.symbols('x')
print(chi_squared_pdf(f"({x}, 3)"), "\n") # 应输出符号表达式
# sqrt(2)*sqrt(x)*exp(-x/2)/(2*sqrt(pi))
if __name__ == "__main__":
main()
卡方分布的随机抽样
r=ChiSquareRND(k,sz)从卡方分布生成随机数的数组,其中向量sz指定大小(r).
k是自由度,正标量值,正标量值数组.
sz是每个维度的大小(作为行向量),整数的行向量
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from scipy.stats import chi2
def chi_squared_rnd(input_str):
"""
生成卡方分布的随机数矩阵
参数:
input_str: 输入字符串,格式应为(k, [m,n])元组,例如 "(3, [2,3])"
返回:
sp.Matrix 或 错误信息字符串
处理逻辑:
1. 验证输入格式为(k, 矩阵尺寸)
2. 检查k为正整数
3. 生成指定尺寸的卡方分布随机数矩阵
"""
try:
expr = sp.sympify(input_str)
error = False
result = None
# 检查输入是否为(k, 尺寸)元组
if isinstance(expr, tuple) and len(expr) == 2:
k, sz = expr[0], expr[1]
# 验证k参数
if not (k.is_integer and k > 0):
return f"错误: 自由度k必须为正整数,当前k={k}"
# 验证尺寸参数
if isinstance(sz, list) and len(sz) == 2:
size = tuple(int(e.evalf()) for e in sz)
"""用SciPy生成卡方分布的随机数(标量输出)"""
result = chi2.rvs(df=int(k), size=size)
'''
此处是sympy实现
chi_squared = sp.stats.ChiSquared('ChiSquared', k_val)
iterator = sp.stats.sample_iter(chi_squared, numsamples=1)
return list(iterator)[0]
'''
else:
error = True
else:
error = True
return result if not error else f"输入格式错误: 需要(k, [m,n])元组,当前输入{input_str}"
except Exception as e:
return f"错误:{e}"
def main():
"""测试用例主函数"""
# 测试1: 有效输入
print("测试1: 2x3矩阵")
print(chi_squared_rnd("(3, [2,3])"), "\n") # 应输出2x3随机矩阵
# [[4.03513455 1.70488102 1.05668236]
# [5.22645923 3.76494573 8.59081048]]
# 测试2: 边界情况测试
print("测试2: 1x1矩阵")
print(chi_squared_rnd("(1, [1,1])"), "\n") # 应输出1x1矩阵
# [[0.03386891]]
if __name__ == "__main__":
main()
乔列斯基分解
chol(A) A是输入矩阵,可以使用满存储或稀疏存储,但必须为方阵和对称正定矩阵.
chol 假设A是对称实矩阵,或者是Hermitian对称复矩阵.chol仅使用A的上三角或下三角执行计算,具体取决于triangle的值.
将正定对称矩阵分解为一个下三角矩阵及其转置的上三角矩阵乘积.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
from scipy.linalg import cholesky
def cholesky_matrix(input_str):
"""
执行矩阵的Cholesky分解
参数:
input_str: 输入矩阵的字符串表示,可以是符号矩阵或数值矩阵
返回:
sp.Matrix 或 str: 成功返回下三角矩阵,失败返回错误信息
处理逻辑:
1. 将输入转换为SymPy矩阵
2. 检查矩阵是否对称正定
3. 符号矩阵使用SymPy分解
4. 数值矩阵使用NumPy分解(更高效)
"""
try:
expr = sp.sympify(input_str)
result = None
# 转换为SymPy矩阵
if isinstance(expr, list):
A = sp.Matrix(expr)
else:
return f"输入错误: 无法转换为矩阵 - {input_str}"
# 检查矩阵是否为方阵
if A.rows != A.cols:
return f"错误: 矩阵必须是方阵,当前尺寸为{A.rows}x{A.cols}"
# 检查是否包含符号变量
contains_symbols = any((element.has(sp.I) or element.free_symbols) for element in A)
if contains_symbols:
result = A.cholesky()
else:
N_A = np.array(A, dtype=float)
c = cholesky(N_A)
result = sp.Matrix(c)
return result
except Exception as e:
return f"错误: {e}"
def main():
"""测试用例主函数"""
# 测试1: 有效数值矩阵
print("测试1: 4x4数值矩阵")
print(cholesky_matrix("[[4,12,-16],[12,37,-43],[-16,-43,98]]"), "\n")
# Matrix([[2.00000000000000, 6.00000000000000, -8.00000000000000],
# [0, 1.00000000000000, 5.00000000000000],
# [0, 0, 3.00000000000000]])
# 测试2: 符号矩阵
print("测试2: 复数矩阵分解")
print(cholesky_matrix(f"[[9, 3j],[-3j,5]]"), "\n")
# Matrix([[3, 0], [-I, 2]])
if __name__ == "__main__":
main()
乔列斯基分解的秩1更新
R1 = cholupdate(R,x)(其中 R = chol(A) 是A的原始乔列斯基分解)返回 A + x*x' 的上三角乔列斯基因子,其中x是具有合适长度的一个列向量.cholupdate仅使用R的对角线和上三角.R 的下三角将被忽略.
R1 = cholupdate(R,x,'+') 与 R1 = cholupdate(R,x) 相同.
R1 = cholupdate(R,x,'-') 返回 A - x*x' 的乔列斯基因子.当R不是有效的乔列斯基因子或旧矩阵不是正定矩阵时,将会报告一条错误消息,这样将没有乔列斯基分解
cholupdate 仅适用于满矩阵.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cholesky_update_rank(input_str):
"""
执行 Cholesky 分解的秩-1 更新或降级。
参数:
input_str (str): 输入字符串,格式为表示元组的字符串。
示例: "([[4,0], [0,9]], [2,3], '+')" 表示:
- L: 下三角矩阵 [[4,0], [0,9]]
- x: 向量 [2,3]
- sign: '+' 表示更新
返回:
sp.Matrix 或 str: 成功返回更新后的矩阵,失败返回错误信息。
"""
try:
# 解析输入字符串为Python对象(如元组、列表)
expr = sp.sympify(input_str)
error = False
result = None
def evaluation_cholupdate(L, x, sign='+'):
"""
内部函数:执行 Cholesky 秩-1 更新/降级算法。
参数:
L (np.ndarray): 下三角矩阵
x (np.ndarray): 更新向量
sign (str): 操作符 '+' 或 '-'
返回:
np.ndarray: 更新后的下三角矩阵
"""
p = len(x)
x = x.copy() # 避免修改原向量
for k in range(p):
if sign == '+':
r = np.sqrt(L[k, k] ** 2 + x[k] ** 2)
elif sign == '-':
r = np.sqrt(L[k, k] ** 2 - x[k] ** 2)
else:
raise ValueError("Invalid sign")
c = r / L[k, k]
s = x[k] / L[k, k]
L[k, k] = r
if k + 1 < p:
L[k, k + 1:p] = (L[k, k + 1:p] + s * x[k + 1:p]) / c
x[k + 1:p] = c * x[k + 1:p] - s * L[k, k + 1:p]
return L
# 检查输入结构是否为元组
if isinstance(expr, tuple):
# 处理两种输入形式:(L, x) 或 (L, x, sign)
if len(expr) == 2:
L, x = expr[0], expr[1]
sign = '+' # 默认符号为+
elif len(expr) == 3:
L, x, sign_symbol = expr[0], expr[1], expr[2]
if str(sign_symbol) == "plus":
sign = '+' # 默认符号为+
elif str(sign_symbol) == "minus":
sign = '-' # 默认符号为+
else:
error = True
else:
error = True
# 转换为 SymPy 矩阵
L_matrix = sp.Matrix(L)
x_matrix = sp.Matrix(x)
# 检查矩阵有效性
if not error and L_matrix is not None and x_matrix is not None:
# 转换为 NumPy 数组
np_L = np.array(L_matrix.tolist(), dtype=float)
np_x = np.ravel(np.array(x_matrix.tolist(), dtype=float))
# 执行 Cholesky 更新
try:
result = evaluation_cholupdate(np_L.T, np_x, sign)
except ValueError as e:
error = True
return f"计算错误: {e}"
else:
error = True
else:
error = True
# 返回结果或错误
if not error and result is not None:
return sp.Matrix(result.tolist())
else:
return f"输入错误: {input_str}"
except (SyntaxError, ValueError, TypeError) as e:
return f"解析错误: {e}"
except Exception as e:
return f"未知错误: {e}"
def main():
# 示例1: 正确输入(秩-1更新)
input_str1 = "[[4.0, 0.0], [0.0, 9.0]],[2.0, 3.0],plus"
print("示例1 输入:", input_str1)
result1 = cholesky_update_rank(input_str1)
print("更新结果:\n", result1 if isinstance(result1, sp.Matrix) else result1)
# Matrix([[4.47213595499958, 1.34164078649987],
# [0, 9.39148550549912]])
# 示例2: 正确输入(秩-1降级)
input_str2 = "([[2.0, 0.0], [0.0, 3.0]], [1.0, 1.0], minus)"
print("\n示例2 输入:", input_str2)
result2 = cholesky_update_rank(input_str2)
print("降级结果:\n", result2 if isinstance(result2, sp.Matrix) else result2)
# Matrix([[1.73205080756888, 0.577350269189626],
# [0, 2.94392028877595]])
if __name__ == "__main__":
main()
奇异的托普利茨下黑森贝格矩阵
A = chow(n,alpha,delta) 返回一个阶数为 n 的 Chow 矩阵,它是 n×n 的下黑森贝格矩阵, alpha 和 delta 使用默认值 1 和 0.
n,alpha,delta - 输入, 标量.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
def chow_matrix(input_str, locals_dict=None):
"""
根据输入字符串生成 Chow 矩阵。
参数:
input_str: 输入的字符串,可以是以下形式:
- 单个正整数 (如 "5")
- 元组格式,包含1-3个参数 (如 "(3, 2)", "(4, 1, 0.5)")
元组参数意义:(矩阵维度n, 对角线元素alpha=1, 下三角元素delta=0)
locals_dict: 用于符号解析的本地变量字典,默认为 None
返回:
生成的 SymPy 矩阵,若输入错误则返回错误信息字符串
"""
try:
# 解析输入字符串
expr = sp.sympify(input_str)
error = False
result = None
def generate_chow(n, alpha=1, delta=0):
"""生成 n x n 的 Chow 矩阵"""
# 输入验证
if not isinstance(n, int) or n <= 0:
raise ValueError("矩阵维度n必须是正整数")
# 使用 SymPy 创建矩阵
C = sp.Matrix.zeros(n, n)
for i in range(n):
for j in range(n):
if i == j:
C[i, j] = alpha
elif i > j:
C[i, j] = delta
else:
C[i, j] = 1
return C
# 处理不同输入类型
if isinstance(expr, tuple):
# 元组输入 (n, alpha, delta)
params = list(expr)
if len(params) < 1 or len(params) > 3:
error = True
else:
try:
n = int(params[0]) if params[0].is_integer else params[0]
alpha = params[1] if len(params) >= 2 else 1
delta = params[2] if len(params) >= 3 else 0
result = generate_chow(n, alpha, delta)
except (TypeError, ValueError):
error = True
elif expr.is_number and expr.is_integer:
# 单个整数输入
n = int(expr)
result = generate_chow(n)
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
def main():
# 示例1: 3x3 默认参数矩阵
input1 = "3"
print(f"输入: {input1}\n输出:\n{chow_matrix(input1)}\n")
# Matrix([[1, 1, 1], [0, 1, 1], [0, 0, 1]])
# 示例2: 2x2 带alpha参数的矩阵
input2 = "(2, 5)"
print(f"输入: {input2}\n输出:\n{chow_matrix(input2)}\n")
# Matrix([[5, 1], [0, 5]])
# 示例3: 4x4 完整参数矩阵
input3 = "(4, 1, 0.5)"
print(f"输入: {input3}\n输出:\n{chow_matrix(input3)}\n")
#Matrix([[1, 1, 1, 1],
# [0.500000000000000, 1, 1, 1],
# [0.500000000000000, 0.500000000000000, 1, 1],
# [0.500000000000000, 0.500000000000000, 0.500000000000000, 1]])
if __name__ == "__main__":
main()
循环矩阵
A = circul(v) 返回一个n×n循环矩阵, 其第一行是长度为n的向量v. 循环矩阵是一种特殊的托普利茨矩阵,其中每行都通过周期性地将上一行中的各元向右移一位来获得.
如果v是标量,则 A = circul(1:v)。
v - 输入, 标量, 向量
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def circul_matrix(input_str, locals_dict=None):
"""
根据输入生成循环矩阵
参数:
input_str - 输入字符串,支持以下格式:
1. 单个正整数 (如 "3" 生成向量[1,2,3]的循环矩阵)
2. 列表形式 (如 "[1, 2, 3]" 或 "Matrix([a, b, c])")
3. 符号表达式 (需通过locals_dict提供符号定义)
locals_dict - 符号解析字典,默认为None
返回:
SymPy矩阵对象 或 错误信息字符串
"""
try:
# 解析输入表达式
expr = sp.sympify(input_str)
error = False
result = None
def generate_circulant(vector):
"""生成循环矩阵的核心函数"""
n = len(vector)
# 使用SymPy矩阵代替numpy
C = sp.Matrix.zeros(n, n)
for i in range(n):
# 实现循环右移操作
for j in range(n):
C[i, j] = vector[(j - i) % n]
return C
# 处理不同输入类型
if isinstance(expr, sp.Matrix):
# 直接处理矩阵输入
if expr.rows == 1 or expr.cols == 1:
vector = list(expr)
result = generate_circulant(vector)
else:
error = True
elif isinstance(expr, list):
# 处理列表输入
# 尝试转换为数值或符号列表
vector = [sp.sympify(e) for e in expr]
result = generate_circulant(vector)
elif expr.is_integer and expr > 0:
# 生成1到n的序列
v = list(range(1, int(expr) + 1))
n_v = np.array(v, dtype=float)
result = generate_circulant(vector=n_v)
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {str(e)}"
def main():
# 示例1: 数值列表输入
input1 = "[1, 2, 3]"
print(f"输入: {input1}\n输出:\n{circul_matrix(input1)}\n")
# Matrix([[1, 2, 3], [3, 1, 2], [2, 3, 1]])
# 示例2: 符号输入
a, b, c = sp.symbols('a b c')
input2 = "Matrix([a, b, c])"
print(f"输入: {input2}\n输出:\n{circul_matrix(input2, locals_dict={'a': a, 'b': b, 'c': c})}\n")
# Matrix([[a, b, c], [c, a, b], [b, c, a]])
# 示例3: 数值简写输入
input3 = "3"
print(f"输入: {input3}\n输出:\n{circul_matrix(input3)}\n")
# Matrix([[1.00000000000000, 2.00000000000000, 3.00000000000000],
# [3.00000000000000, 1.00000000000000, 2.00000000000000],
# [2.00000000000000, 3.00000000000000, 1.00000000000000]])
# 示例4: 三角函数表达式
x = sp.symbols('x')
input4 = "[sin(x), cos(x), 2*sin(x)]"
print(f"输入: {input4}\n输出:\n{circul_matrix(input4, {'x': x})}\n")
# Matrix([[sin(x), cos(x), 2*sin(x)],
# [2*sin(x), sin(x), cos(x)],
# [cos(x), 2*sin(x), sin(x)]])
if __name__ == "__main__":
main()
具有零值对角线元的Clement三对角矩阵
A = clement(n,k) 返回一个主对角线元为0的n×n三对角矩阵. 对于 k = 0(默认值),A 是非对称的.对于 k = 1,A 是对称的.
A = clement(n,k,1) 在对角线方面类似于 clement('clement',n,0),其中存在一个具有相同大小的对角线矩阵 D 满足 B = inv(D)*A*D.
如果n是奇数, 则A是奇异矩阵.
A 的特征值是显式可知的, 其中包括正负数字 n-1、n-3、n-5、...、1 或 0.
n, k - 输入, 标量
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def clement_matrix(input_str, locals_dict=None):
"""
生成 Clement 三对角矩阵 (对称或非对称版本)
参数:
input_str - 输入字符串,支持格式:
1. 单个正整数 n (如 "4")
2. 元组 (n, k) (如 "(4, 1)")
k=0: 非对称矩阵 (默认)
k=1: 对称矩阵
locals_dict - 符号解析字典,默认为None
返回:
SymPy矩阵对象 或 错误信息字符串
"""
try:
# 解析输入表达式
expr = sp.sympify(input_str)
error = False
result = None
def generate_clement(n, k=0):
"""生成 Clement 矩阵核心函数"""
# 输入验证
if not isinstance(n, int) or n < 2:
raise ValueError("矩阵维度n必须是≥2的整数")
if k not in (0, 1):
raise ValueError("参数k只能是0或1")
# 使用SymPy创建矩阵
A = sp.Matrix.zeros(n, n)
for i in range(n - 1):
val = sp.sqrt((n - i - 1) * (i + 1))
A[i, i + 1] = val
A[i + 1, i] = val if k == 1 else -val
return A
# 处理不同输入类型
if isinstance(expr, tuple):
# 元组输入 (n, k)
if len(expr) != 2:
error = True
else:
try:
n = int(expr[0]) if expr[0].is_integer else expr[0]
k = int(expr[1]) if expr[1].is_number else expr[1]
result = generate_clement(n, k)
except (TypeError, ValueError):
error = True
elif expr.is_integer and expr >= 2:
# 单个整数输入
n = int(expr)
result = generate_clement(n)
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {str(e)}"
def main():
# 示例1: 4阶非对称矩阵 (默认k=0)
input1 = "4"
print(f"输入: {input1}\n输出:\n{clement_matrix(input1)}\n")
# Matrix([[0, sqrt(3), 0, 0],
# [-sqrt(3), 0, 2, 0],
# [0, -2, 0, sqrt(3)],
# [0, 0, -sqrt(3), 0]])
# 示例2: 3阶对称矩阵
input2 = "(3, 1)"
print(f"输入: {input2}\n输出:\n{clement_matrix(input2)}\n")
# Matrix([[0, sqrt(2), 0],
# [sqrt(2), 0, sqrt(2)],
# [0, sqrt(2), 0]])
if __name__ == "__main__":
main()
余弦积分
cosint(X)返回X的余弦积分函数
根据其参数,余弦返回浮点或精确的符号结果.
X是符号变量,符号表达式,函数,向量或矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from sympy.functions.special.error_functions import Ci
from scipy.special import sici
def ci_cosine_integral(input_str):
"""
计算输入的余弦积分Ci(x),支持矩阵、数值和符号表达式
参数:
input_str: 输入的字符串表达式,可以是矩阵、数值或符号表达式
返回:
计算结果。如果输入为矩阵,返回对应元素的Ci积分矩阵;
如果输入为数值或符号,返回Ci积分值。
无法处理时返回错误信息字符串
"""
try:
# 表达式转换
expr = sp.sympify(input_str)
error = False
result = None
# 元组类型直接视为错误
if isinstance(expr, tuple):
error = True
# 处理标量数值和符号表达式
elif expr.is_number:
z = complex(expr)
"""计算余弦积分 Ci(x)"""
result = sici(z)[1] # 取返回值的第二个元素,即 Ci(x)
elif expr.free_symbols:
# 处理符号变量表达式
result = Ci(expr)
else:
error = True
return result if not error else f"输入错误: {input_str}"
except sp.SympifyError as e:
return f"表达式解析错误: {e}"
except Exception as e:
return f"运行时错误: {str(e)}"
def main():
"""
主函数测试用例
"""
test_cases = [
"0", # (-inf+nan*j)
"x", # Ci(x)
"3.14", # (0.07417499776126246+0j)
"cos(2)" # (-0.3424847875188666+3.141592653589793j)
]
for case in test_cases:
print(f"测试输入: {case}")
result = ci_cosine_integral(case)
print("返回结果:")
# 统一输出格式
if isinstance(result, sp.Matrix):
sp.pprint(result)
elif isinstance(result, sp.Expr):
print(sp.pretty(result))
else:
print(result)
print("-" * 50)
if __name__ == "__main__":
main()
以弧度为单位的参量的余弦.
Y = cos(X)返回X的每个元素的余弦.cos函数按元素处理数组.该函数同时接受实数和复数输入.
对于X的实数值,cos(X)返回区间[-1, 1]内的实数值.
对于X的复数值,cos(X)返回复数值.
X是标量,向量,数组,矩阵.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cosine_trig_function(input_str):
"""
计算输入表达式或矩阵的余弦值。
参数:
input_str: 输入的字符串,可以是数值、符号表达式或矩阵。
返回:
计算结果(数值、符号表达式或矩阵),若输入不合法则返回错误信息。
"""
try:
# 将输入字符串转换为 SymPy 表达式
expr = sp.sympify(input_str)
error = False
result = None
# 处理数值或符号表达式
if expr.free_symbols:
# 计算余弦并数值化(若为符号表达式则保留符号形式)
result = sp.cos(expr)
elif expr.is_number:
z = complex(expr)
result = np.cos(z)
# 其他未知类型标记为错误
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
if __name__ == "__main__":
# 示例1:数值输入(π)
input1 = "2"
print(f"输入:{input1}")
print("输出:", cosine_trig_function(input1)) # 应输出 -1.0
# 输出: (-0.4161468365471424-0j)
# 示例2:符号输入(x)
input2 = "x"
print(f"\n输入:{input2}")
print("输出:", cosine_trig_function(input2)) # 应输出 cos(x)
# 输出: cos(x)
以度为单位的参量的余弦.
Y = cosd(X)返回X的每个元素的余弦.cosd该函数同时接受实数和复数输入.
X是标量,向量,数组,矩阵.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cosd_cosine_degree(input_str):
"""
计算角度(度数)的余弦值,支持矩阵和符号计算
参数:
input_str: 输入字符串,可以是:
- 数值(如 "30")
- 符号表达式(如 "x")
- 矩阵(如 "[[30, 60], [0, 90]]")
返回:
计算结果(数值/符号/矩阵)或错误信息
"""
try:
expr = sp.sympify(input_str)
error = False
result = None
# 数值/符号处理分支
if expr.free_symbols:
result = sp.cos(expr * sp.pi / 180)
elif expr.is_number:
z = complex(expr)
result = np.cos(z * np.pi / 180)
# 未知类型标记为错误
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
if __name__ == "__main__":
# 示例1:基本数值计算
print("示例1:", cosd_cosine_degree("30"))
# (0.8660254037844387-0j)
# 示例2:符号运算
print("\n示例3:", cosd_cosine_degree("x"))
# cos(pi*x/180)
双曲余弦函数.
Y = cosh(X)返回X的每个元素的双曲余弦.cosh该函数同时接受实数和复数输入,所有的角度都以弧度表示.
X是标量,向量,数组,矩阵.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cosh_hyperbolic_cosine(input_str):
"""
计算输入表达式的双曲余弦值,支持矩阵、数值和符号表达式。
参数:
input_str: 输入的字符串表达式,可以是矩阵、数值或符号表达式。
返回:
计算结果。如果输入为矩阵,返回对应元素的cosh矩阵;如果输入为数值或符号,返回cosh值。
如果输入无法解析或处理,返回错误信息字符串。
"""
try:
# 将输入字符串转换为SymPy表达式
expr = sp.sympify(input_str)
error = False
result = None
# 处理数值或符号表达式
if expr.free_symbols:
result = sp.cosh(expr)
elif expr.is_number:
z = complex(expr)
result = np.cosh(z)
# 其他情况视为错误
else:
error = True
# 根据错误标志返回结果或错误信息
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
def main():
"""
主函数,用于测试cosh_hyperbolic_cosine函数的各种用例。
"""
test_cases = [
"3",
# (10.067661995777765+0j)
"3+2j",
# (-4.189625690968807+9.109227893755337j)
"x",
# cosh(x)
"cosh(0)",
# (1.5430806348152437+0j)
]
for case in test_cases:
print(f"测试输入: {case}")
result = cosh_hyperbolic_cosine(case)
print("返回结果:")
# 统一处理结果的打印格式
if isinstance(result, sp.Matrix):
sp.pprint(result)
else:
print(f"{result}\n")
print("-" * 50)
if __name__ == "__main__":
main()
双曲余弦积分
如果x是浮点数,则Chi(x)返回浮点结果.
Y = Chi(x)返回算术表达式
x是标量,符号变量,表达式,向量,矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from sympy.functions.special.error_functions import Chi
from scipy.special import shichi
def chi_hyper_cosine_integral(input_str):
"""
计算输入的双曲余弦积分Chi(x),支持矩阵、数值和符号表达式
参数:
input_str: 输入的字符串表达式,可以是矩阵、数值或符号表达式
返回:
计算结果。如果输入为矩阵,返回对应元素的Chi积分矩阵;
如果输入为数值或符号,返回Chi积分值。
无法处理时返回错误信息字符串
"""
try:
# 表达式转换
expr = sp.sympify(input_str)
error = False
result = None
# 处理标量数值和符号表达式
if expr.free_symbols:
result = Chi(expr)
elif expr.is_number:
z = complex(expr)
Shi_, Chi_ = shichi(z) # 解包返回值
result = Chi_
else:
error = True
return result if not error else f"输入错误: {input_str}"
except sp.SympifyError as e:
return f"表达式解析错误: {e}"
except Exception as e:
return f"运行时错误: {str(e)}"
def main():
"""
主函数测试用例
"""
test_cases = [
"0",
# (-inf+nan*j)
"2+2j",
# (0.9629226258960547+2.6677809260012038j)
"x",
# Chi(x)
"Chi(0)",
# (nan+nan*j)
"3.14"
# (5.452860589178992+0j)
]
for case in test_cases:
print(f"测试输入: {case}")
result = chi_hyper_cosine_integral(case)
print("返回结果:")
# 统一输出格式
if isinstance(result, sp.Matrix):
sp.pprint(result)
elif isinstance(result, sp.Expr):
print(sp.pretty(result))
else:
print(result)
print("-" * 50)
if __name__ == "__main__":
main()
准确计算cos(x*pi).
Y = cospi(X).该函数同时接受实数和复数输入.
X是标量,向量,数组,矩阵.
对于奇数,cospi(n/2) 正好为零.
对于整数,cospi(n) 为+1或-1
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cos_pi_cosine(input_str):
"""
计算表达式或矩阵中每个元素的cos(pi * x)
参数:
input_str: 输入的字符串,可以是数值、符号表达式、列表或矩阵
返回:
计算结果,如果输入无效则返回错误信息字符串
"""
try:
# 将输入字符串转换为SymPy表达式
expr = sp.sympify(input_str)
error = False
result = None
# 检查输入是否为元组(不支持的类型)
if isinstance(expr, tuple):
error = True
# 处理数值或符号表达式
elif expr.is_number:
z = complex(expr)
result = np.cos(z * np.pi)
elif expr.free_symbols:
result = sp.cos(expr * sp.pi)
else:
# 其他无效类型
error = True
# 根据错误标志返回结果或错误信息
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
def main():
# 示例测试
test_cases = [
"2", # (1+0j)
"x", # cos(pi*x)
]
for case in test_cases:
print(f"输入: {case}")
result = cos_pi_cosine(case)
print("结果:")
if isinstance(result, sp.Matrix):
sp.pprint(result)
else:
print(result)
print("\n" + "-" * 50 + "\n")
if __name__ == "__main__":
main()
角的余切(以弧度为单位)
Y = cot(X) 返回 X 的各元素的余切。cot 函数按元素处理数组。该函数同时接受实数和复数输入。
对于 X 的实数值,cot(X) 返回区间 [-∞, ∞] 内的实数值。
对于 X 的复数值,cot(X) 返回复数值。
X — 输入角(以弧度为单位)标量 | 向量 | 矩阵
Y — 输入角的余切. 标量 | 向量 | 矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from sympy import sympify
import numpy as np
def cotangent_of_radians(input_str):
"""
计算输入表达式(数值或矩阵)的余切值(以弧度为单位)
参数:
input_str: 输入的字符串,可以是数值、矩阵的字符串表示或符号表达式
返回:
计算结果,若输入有效则返回SymPy表达式或矩阵;否则返回错误信息字符串
"""
try:
expr = sympify(input_str)
error = False
result = None
# 元组类型直接判定为无效输入
if isinstance(expr, tuple):
error = True
elif expr.is_number:
z = complex(expr)
result = 1 / np.tan(z)
elif expr.free_symbols:
# 处理数值或符号表达式
result = sp.cot(expr)
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
if __name__ == "__main__":
# 示例测试
print("===== 测试1:数值计算 =====")
test_cases = [
("pi/4", "1.0 (cot(pi/4))"),
# 结果: (1.0000000000000002+0j)
("0", "无穷大 (cot(0))"),
# 结果: (inf+nan*j)
("pi/2", "0 (cot(pi/2))")
# 结果: (6.123233995736766e-17+0j)
]
for inp, desc in test_cases:
print(f"\n输入: {inp} ({desc})")
result = cotangent_of_radians(inp)
print("结果:", result)
print("\n===== 测试3:符号表达式 =====")
sym_input = "x"
print(f"\n输入符号: {sym_input}")
print("结果:", cotangent_of_radians(sym_input))
以度为单位的参量的余切
Y = cotd(X) 返回 X 的元素的余切(以度为单位)
X — 以度为单位的角, 标量值 | 向量 | 矩阵
Y — 角余切, 标量值 | 向量 | 矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from sympy import sympify
import numpy as np
def cotangent_degree_radians(input_str):
"""
计算输入的角度(度数)的余切值,支持矩阵、数值和符号表达式
参数:
input_str: 输入字符串,可以是数值、符号或矩阵表达式
返回:
计算结果(数值、矩阵或符号表达式)或错误信息字符串
"""
try:
expr = sympify(input_str) # 将输入字符串转换为SymPy表达式
error = False
result = None
# 检查输入类型
if expr.is_number:
z = complex(expr)
complex_angle = z * np.pi / 180
result = 1 / np.tan(complex_angle)
elif expr.free_symbols: # 数值或符号处理
rad_z = sp.rad(expr) # 更清晰的写法
result = sp.cot(rad_z)
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
def main():
"""主函数:演示cotangent_degree_radians的使用"""
examples = [
"30",
# (1.7320508075688776+0j)
"45",
# (1.0000000000000002+0j)
"x",
# cot(pi*invalid/180)
]
for example in examples:
print(f"输入: {example}")
result = cotangent_degree_radians(example)
print("结果:")
print(result) # 使用SymPy的美化打印
print("\n" + "=" * 50 + "\n")
if __name__ == "__main__":
main()
双曲余切
Y=coth(X)返回X元素的双曲正切。coth函数对数组进行元素操作。该函数接受真实和复杂的输入。所有角度均以弧度为单位。
X —— 以弧度为单位的输入角度,标量|矢量|矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
from sympy import sympify
import numpy as np
def cotangent_hyperbolic_radians(input_str):
"""
计算输入的双曲余切值(coth),支持数值、符号和矩阵输入
参数:
input_str: 输入字符串,可以是数值、符号或矩阵表达式
返回:
计算结果(数值、矩阵或符号表达式)或错误信息
"""
try:
expr = sympify(input_str) # 将输入字符串转换为SymPy表达式
error = False
result = None
# 检查输入类型
if expr.is_number:
z = complex(expr)
result = 1 / np.tanh(z)
elif expr.free_symbols: # 数值或符号处理
result = sp.coth(expr)
else:
error = True # 未知类型标记为错误
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {str(e)}" # 返回异常信息
def main():
"""主函数:演示双曲余切函数功能"""
test_cases = [
"1", # (1.3130352854993315+0j)
"0", # (inf+nan*j)
"x", # coth(x)
]
for case in test_cases:
print(f"输入: {case}")
result = cotangent_hyperbolic_radians(case)
print("结果:")
print(result) # 使用SymPy的美化打印
print("\n" + "=" * 50 + "\n")
if __name__ == "__main__":
main()
协方差
C = cov(A) 返回协方差.
如果 A 是由观测值组成的向量,则 C 为标量值方差.
如果 A 是其列表示随机变量或行表示观测值的矩阵,则 C 为对应的列方差沿着对角线排列的协方差矩阵.
C = cov(A,B) 返回两个随机变量 A 和 B 之间的协方差
如果A和B是长度相同的观测值向量,则cov(A,B)为2×2协方差矩阵
C = cov(___,w) 为之前的任何语法指定归一化权重.如果 w = 0(默认值),则 C 按观测值数量-1实现归一化. w=1时,按观测值数量对它实现归一化.
A —— 输入数组 向量|矩阵
B —— 附加输入数组向量|矩阵
w —— 归一化权重0(默认值)|1
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
from sympy import sympify
def covariance_array(input_str):
"""
计算输入数据集的协方差矩阵(仅支持数值矩阵)
参数格式支持:
- 单个矩阵:计算该矩阵的协方差(默认归一化方式,ddof=1)
- 元组格式:
(A, B, flag): 两个矩阵A和B的协方差,flag为0或1指定归一化方式
(A, B): 两个矩阵的协方差(默认ddof=1)
(A, flag): 单个矩阵A的协方差,flag指定归一化方式
参数说明:
flag=0: 使用N-1归一化(无偏估计,ddof=1)
flag=1: 使用N归一化(有偏估计,ddof=0)
返回:
NumPy协方差矩阵 或 错误信息字符串
"""
try:
expr = sympify(input_str)
error = False
result = None
def validate_and_convert(matrix):
"""验证矩阵是否为纯数值并转换为NumPy数组"""
if matrix.is_symbolic():
raise ValueError("矩阵包含符号,无法转换为数值数组")
else:
return np.array(matrix, dtype=float)
# 处理元组输入
if isinstance(expr, tuple):
if len(expr) > 2:
if int(expr[2]) not in [0, 1]:
error = True
if isinstance(expr[0], list) and isinstance(expr[1], list):
A = sp.Matrix(expr[0])
B = sp.Matrix(expr[1])
if A.shape == B.shape:
data_a = validate_and_convert(A)
data_b = validate_and_convert(B)
result = np.cov(data_a, data_b, rowvar=False, ddof=1 - int(expr[2]))
else:
error = True
elif isinstance(expr[0], list) and isinstance(expr[1], list):
A = sp.Matrix(expr[0])
B = sp.Matrix(expr[1])
if A.shape == B.shape:
data_a = validate_and_convert(A)
data_b = validate_and_convert(B)
result = np.cov(data_a, data_b, rowvar=False)
elif isinstance(expr[0], list) and int(expr[1]) in [0, 1]:
A = sp.Matrix(expr[0])
data_a = validate_and_convert(A)
result = np.cov(data_a, rowvar=False, ddof=1 - int(expr[1]))
elif isinstance(expr, list):
A = sp.Matrix(expr)
data_a = validate_and_convert(A)
result = np.cov(data_a, rowvar=False)
else:
error = True
if error:
return f"输入错误: {input_str}"
return result
except Exception as e:
return f"错误: {str(e)}"
def main():
"""主函数:演示协方差计算功能"""
test_cases = [
# 有效输入测试
"[[1,2], [3,4], [5,6]]",
# 结果:
#[[4. 4.]
# [4. 4.]]
"[[1,2], [3,4]],[[5,6], [7,8]]",
# 结果:
# [[2. 2. 2. 2.]
# [2. 2. 2. 2.]
# [2. 2. 2. 2.]
# [2. 2. 2. 2.]]
"[[1,2], [3,4]],[[5,6], [7,8]], 0",
# 结果:
# [[2. 2. 2. 2.]
# [2. 2. 2. 2.]
# [2. 2. 2. 2.]
# [2. 2. 2. 2.]]
"[[1,2],[3,4]], 0",
# 结果:
# [[2. 2.]
# [2. 2.]]
]
for case in test_cases:
print(f"输入: {case}")
result = covariance_array(case)
print("结果:")
if isinstance(result, str):
print(result)
else:
print(np.round(result, 4)) # 保留4位小数便于观察
print("\n" + "=" * 50 + "\n")
if __name__ == "__main__":
main()
将复数排序为复共轭对组
B = cplxpair(A) 对沿复数数组不同维度的元素排序,并将复共轭对组组合在一起。
共轭对组按递增实部排序。在对组中,带有负虚部的元素排在前面。在所有复数对组后返回纯实数值。复共轭对组会强制成为精确复共轭。相对于 100*eps 的默认容差 abs(A(i)) 确定哪些数字是实数,哪些元素是成对复共轭。
如果 A 为向量,cplxpair(A) 返回复共轭对组组合在一起的 A。
如果 A 是矩阵,则 cplxpair(A) 返回其列已排序且复共轭已配对的 A。
B = cplxpair(A,tol) 覆盖默认容差。
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import numpy as np
import sympy as sp
def complex_conjugate_pairs(input_str):
"""
实现MATLAB cplxpair函数,将复数数组排序并配对共轭复数
参数:
input_str (str): 输入表达式,如 "A, tol"
返回:
sp.Matrix: 排序后的矩阵,共轭对相邻
异常:
ValueError: 输入不合法或无法配对
"""
try:
# 解析输入参数
expr = sp.sympify(input_str)
error = False
result = None
tol = 1e-6 # 默认容差
def cplxpair(A, tol=1e-10):
"""
MATLAB cplxpair函数的NumPy实现
参数:
A: 输入数组(向量、矩阵或多维数组)
tol: 容差,用于判断两个复数是否共轭
返回:
按共轭对排序的数组
"""
A = np.asarray(A)
# 处理空数组
if A.size == 0:
return A
# 确定第一个非单一维度
dim = next((i for i, s in enumerate(A.shape) if s > 1), 0)
# 对于向量输入,直接处理
if A.ndim == 1:
return _sort_complex_vector(A, tol)
# 对于多维数组,沿第一个非单一维度处理
else:
# 转置数组,使目标维度成为第一个维度
transpose_axes = list(range(A.ndim))
transpose_axes.insert(0, dim)
transpose_axes.pop(dim + 1)
A_transposed = A.transpose(transpose_axes)
# 重塑为二维数组(第一个维度为向量,其余维度合并)
original_shape = A_transposed.shape
A_2d = A_transposed.reshape(original_shape[0], -1)
# 对每一列应用排序
sorted_2d = np.apply_along_axis(lambda x: _sort_complex_vector(x, tol), 0, A_2d)
# 重塑回原始形状(转置后)
sorted_transposed = sorted_2d.reshape(original_shape)
# 转回原始维度顺序
inverse_transpose = [transpose_axes.index(i) for i in range(len(transpose_axes))]
sorted_A = sorted_transposed.transpose(inverse_transpose)
return sorted_A
def _sort_complex_vector(c, tol):
"""辅助函数:对复数向量进行共轭对排序"""
# 分离实部和虚部
real_part = np.real(c)
imag_part = np.imag(c)
# 创建排序索引:先按实部升序,再按虚部绝对值升序
idx = np.lexsort((np.abs(imag_part), real_part))
sorted_c = c[idx].copy() # 复制以避免修改原数组
# 处理共轭对,确保虚部非负的元素在前
n = len(sorted_c)
result = np.zeros(n, dtype=complex)
i = 0
j = 0
while i < n:
# 如果是实数值,直接添加
if np.abs(sorted_c[i].imag) < tol:
result[j] = sorted_c[i]
i += 1
j += 1
else:
# 找到共轭对
found = False
for k in range(i + 1, n):
if (np.abs(np.real(sorted_c[k]) - np.real(sorted_c[i])) < tol and
np.abs(np.imag(sorted_c[k]) + np.imag(sorted_c[i])) < tol):
# 确保虚部非负的元素在前
if sorted_c[i].imag >= 0:
result[j] = sorted_c[i]
result[j + 1] = sorted_c[k]
else:
result[j] = sorted_c[k]
result[j + 1] = sorted_c[i]
i = k + 1
j += 2
found = True
break
if not found:
# 没有找到共轭对,单独添加
result[j] = sorted_c[i]
i += 1
j += 1
return result[:j] # 裁剪到实际填充的部分
if isinstance(expr, tuple):
error = True
elif isinstance(expr, list):
A = np.asarray(expr, dtype=complex)
result = cplxpair(A, tol)
else:
error = True
return result if not error else f"输入错误:{input_str}"
except Exception as e:
raise ValueError(f"cplxpair错误: {str(e)}")
# 示范代码
if __name__ == "__main__":
# 矩阵示例
print("\n=== 矩阵示例 ===")
sorted_matrix = complex_conjugate_pairs("[[3 + 4j, 1 - 2j, 5],[1 + 2j, 3 - 4j, 6j],[7, 8 + 1j, 8 - 1j]]")
print("排序后矩阵:\n", sorted_matrix)
# [[1.+2.j 1.-2.j 0.+6.j]
# [3.+4.j 3.-4.j 5.+0.j]
# [7.+0.j 8.+1.j 8.-1.j]]
# 三维数组示例
print("\n=== 三维数组示例 (2x3x3) ===")
sorted_3d = complex_conjugate_pairs(
"[[[3 + 4j, 1 - 2j, 5],[1 + 2j, 3 - 4j, 6j],[7, 8 + 1j, 8 - 1j]],[[4 + 2j, 9, 2 - 3j],[4 - 2j, 10, 2 + 3j],[11, 12 + 5j, 12 - 5j]]]")
print("排序后三维数组:\n", sorted_3d)
# [[[ 3.+4.j 1.-2.j 2.-3.j]
# [ 1.+2.j 3.-4.j 0.+6.j]
# [ 7.+0.j 8.+1.j 8.-1.j]]
#
# [[ 4.+2.j 9.+0.j 5.+0.j]
# [ 4.-2.j 10.+0.j 2.+3.j]
# [11.+0.j 12.+5.j 12.-5.j]]]
叉积
C = cross(A,B) 返回A和B的叉积.
如果A和B为向量,则它们的长度必须为3.
如果A和B为矩阵,则它们必须具有相同大小.在这种情况下,cross函数将A和B视为三元素向量集合.该函数计算对应向量沿大小等于3的第一个数组维度的叉积.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
def cross_vector(input_str):
"""
计算两个三维向量或矩阵列向量的叉积。
参数:
input_str: 字符串形式的输入,应为包含两个矩阵或向量的元组,例如 "([1,2,3], [4,5,6])"
返回:
如果输入合法,返回叉积结果矩阵;否则返回错误信息字符串。
"""
try:
# 将输入字符串转换为SymPy表达式
expr = sp.sympify(input_str)
result = None
error = False
# 检查是否为包含两个元素的元组
if isinstance(expr, tuple) and len(expr) == 2:
# 转换两个元素为矩阵
A = sp.Matrix(expr[0]) if isinstance(expr[0], list) else None
B = sp.Matrix(expr[1]) if isinstance(expr[1], list) else None
if A is not None and B is not None:
# 处理两个3x1列向量的情况
if A.shape == (3, 1) and B.shape == (3, 1):
result = A.cross(B)
# 处理两个3xn矩阵的情况(按列计算叉积)
elif A.shape == B.shape and A.shape[0] == 3 and A.shape[1] >= 1:
vectors = []
for i in range(A.shape[1]):
a_col = A.col(i)
b_col = B.col(i)
vectors.append(a_col.cross(b_col))
# 水平拼接所有结果列向量
result = sp.Matrix.hstack(*vectors)
else:
error = True
else:
error = True
else:
error = True
if error:
return f"输入格式错误: {input_str}"
else:
return result
except Exception as e:
return f"计算过程中发生错误: {str(e)}"
def main():
"""主函数,展示cross_vector函数的使用示例"""
# 示例1:两个3D向量的叉积
input1 = "([1, 2, 3], [4, 5, 6])"
print(f"输入:{input1}")
print("输出:", cross_vector(input1), "\n")
# 输出: Matrix([[-3],
# [6],
# [-3]])
# 示例2:两个3x2矩阵的列向量叉积
input2 = "([[1, 2], [3, 4], [5, 6]], [[6, 5], [4, 3], [2, 1]])"
print(f"输入:{input2}")
print("输出:\n", cross_vector(input2), "\n")
# Matrix([[-14, -14],
# [28, 28],
# [-14, -14]])
if __name__ == "__main__":
main()
复共轭转置
B = A' 计算A的复共轭转置.
B = ctranspose(A) 是执行A'的替代方法,但很少使用.
A — 输入数组,向量,矩阵.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
def conjugation_transpose_matrix(input_str):
"""
计算输入字符串所表示的矩阵的共轭转置。
参数:
input_str: 输入的字符串,可能表示一个矩阵。
返回:
如果输入是有效的矩阵,则返回其共轭转置矩阵;否则返回错误信息。
"""
try:
# 使用 sympy 的 sympify 函数将输入字符串转换为 SymPy 表达式
expr = sp.sympify(input_str)
# 初始化错误标志和结果变量
error = False
result = None
# 检查转换后的表达式是否为元组
# 如果是元组,说明输入不是有效的矩阵形式,将错误标志设为 True
if isinstance(expr, tuple):
error = True
# 如果是矩阵,则计算其共轭转置
elif isinstance(expr, list):
A = sp.Matrix(expr)
result = A.H
# 若表达式既不是矩阵也不是可转换为矩阵的形式,将错误标志设为 True
else:
error = True
# 如果没有错误,返回计算结果;否则返回错误信息
return result if not error else f"输入错误: {input_str}"
except Exception as e:
# 若在转换或计算过程中出现异常,返回错误信息
return f"错误:{e}"
def main():
"""
主程序,用于测试 conjugation_transpose_matrix 函数。
"""
# 定义测试用的输入字符串
test_inputs = [
"[[1, 2], [3, 4]]",
# Matrix([[1, 3],
# [2, 4]])
]
# 遍历测试输入,调用 conjugation_transpose_matrix 函数并打印结果
for input_str in test_inputs:
result = conjugation_transpose_matrix(input_str)
print(f"输入: {input_str}")
print(f"结果: {result}")
print()
if __name__ == "__main__":
# 调用主程序
main()
M = cummax(A) 返回 A 的累积最大元素。
如果 A 是向量,则 M 是具有相同大小和类型的向量,并且包含 A 的累积最大值。
如果 A 是矩阵,则 M 是具有相同大小和类型的矩阵,并且包含 A 的每列中的累积最大值。
M = cummax(A,dim) 返回沿维度 dim 的累积最大值。例如,如果 A 是矩阵,则 cummin(A,2) 沿 A 的各行返回累积最大值。
M = cummax(___,direction) 可在上述任一语法的基础上指定计算方向。例如,cummin(A,2,"reverse") 通过从尾到头计算 A 的第二个维度返回 A 的累积最大值。
M = cummax(___,nanflag) 指定忽略还是包括 A 中的 NaN 值。例如,cummin(A,"includenan") 在计算每个最大值时包含 NaN 值。默认情况下,cummin 忽略 NaN 值。
A — 输入数组, 向量 | 矩阵
dim — 沿其运算的维度, 正整数标量
direction — 累积方向, "forward" (默认) | "reverse"
nanflag — 缺失值条件, "omitmissing" (默认) | "omitnan" | "includemissing" | "includenan"
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import numpy as np
import sympy as sp
def cumulative_max_symbolic(input_str):
"""
处理符号累积和的入口函数,解析输入参数并调用核心计算函数。
参数:
input_expr: 输入的表达式,可以是矩阵、列表或包含矩阵及参数的元组
返回:
累积和的结果或错误信息
"""
try:
input_expr = sp.sympify(input_str)
result = None
def cummax(A, dim=None, direction='forward', nanflag='propagate'):
"""
MATLAB cummax函数的NumPy实现
参数:
A: 输入数组
dim: 计算累积最大值的维度,默认为第一个非单一维度
direction: 累积方向,'forward'(默认)或'backward'
nanflag: NaN处理方式,'propagate'(默认)或'omitnan'
返回:
与A形状相同的数组,包含累积最大值
"""
A = np.asarray(A)
# 处理dim参数(默认行为:选择第一个非单一维度)
if dim is None:
if A.size == 0:
dim = 0
else:
dim = next((i for i, s in enumerate(A.shape) if s > 1), 0)
# 处理direction参数
if direction == 'backward':
# 对于后向累积,先反转数组,计算前向累积,再反转回来
slices = [slice(None)] * A.ndim
slices[dim] = slice(None, None, -1)
A_reversed = A[tuple(slices)]
if nanflag == 'omitnan':
# 对每个切片单独处理NaN
result = np.apply_along_axis(_cummax_omitnan, dim, A_reversed)
else:
result = np.maximum.accumulate(A_reversed, axis=dim)
# 反转结果恢复原始顺序
result = result[tuple(slices)]
return result
else: # forward
if nanflag == 'omitnan':
# 对每个切片单独处理NaN
return np.apply_along_axis(_cummax_omitnan, dim, A)
else:
return np.maximum.accumulate(A, axis=dim)
def _cummax_omitnan(arr):
"""辅助函数:处理包含NaN的数组,忽略NaN计算累积最大值"""
mask = np.isnan(arr)
if np.all(mask):
return np.full_like(arr, np.nan)
# 找到第一个非NaN值
first_valid = next((i for i, x in enumerate(arr) if not np.isnan(x)), 0)
result = np.full_like(arr, np.nan)
result[first_valid] = arr[first_valid]
# 计算剩余位置的累积最大值
for i in range(first_valid + 1, len(arr)):
if not np.isnan(arr[i]):
result[i] = max(result[i - 1], arr[i])
else:
result[i] = result[i - 1]
return result
# 解析输入表达式
if isinstance(input_expr, tuple):
if not isinstance(input_expr[0], list):
raise ValueError(f"输入错误:{input_str}")
else:
A = sp.Array(input_expr[0])
params = input_expr[1:]
dim = None # 默认让函数内部处理
direction = 'forward'
nanflag = 'includenan'
# 解析参数
for param in params:
if isinstance(param, (int, sp.Integer)):
dim = int(param) - 1
elif str(param).lower() in ['forward', 'reverse']:
direction = str(param).lower()
elif str(param).lower() in ['includenan', 'omitnan']:
nanflag = str(param).lower()
# 参数校验
if dim is not None and dim not in [1, 2]:
return f"错误: 维度参数 dim 必须为 1 或 2,当前为 {dim}"
if direction not in ['forward', 'reverse']:
return f"错误: 方向参数 direction 必须为 'forward' 或 'reverse',当前为 {direction}"
if nanflag not in ['includenan', 'omitnan']:
return f"错误: nanflag 参数无效,当前为 {nanflag}"
# 调用核心计算函数
np_a = np.asarray(A.tolist(), dtype=float)
result = cummax(np_a, dim=dim, direction=direction, nanflag=nanflag)
else:
# 输入为单一矩阵
if not isinstance(input_expr, list):
raise ValueError(f"输入错误:{input_str}")
else:
A = sp.Array(input_expr)
np_a = np.asarray(A.tolist(), dtype=float)
result = cummax(np_a)
return result
except Exception as e:
return f"错误: {e}"
# 三维数组示范代码
if __name__ == "__main__":
# 创建三维示例数组 (2x3x3)
A_3d = "[[[5, 3, 7],[2, 6, 1],[4, 2, 3]],[[8, 1, 5],[9, 4, 6],[3, nan,2]]]"
print("\n=== 三维数组示例 (2x3x3) ===")
print("原始数组:\n", A_3d)
# 默认参数(处理第一个非单一维度,这里是dim=0)
print("\n默认参数 (dim=0):\n", cumulative_max_symbolic(f"{A_3d}"))
# [[[ 5. 3. 7.]
# [ 2. 6. 1.]
# [ 4. 2. 3.]]
#
# [[ 8. 3. 7.]
# [ 9. 6. 6.]
# [ 4. nan 3.]]]
# 后向累积 (direction='backward')
print("\n后向累积 (dim=2, direction='backward'):\n",
cumulative_max_symbolic(f"{A_3d},2,backward"))
# [[[ 5. 3. 7.]
# [ 5. 6. 7.]
# [ 5. 6. 7.]]
#
# [[ 8. 1. 5.]
# [ 9. 4. 6.]
# [ 9. nan 6.]]]
M = cummin(A) 返回 A 的累积最小元素。
如果 A 是向量,则 M 是具有相同大小和类型的向量,并且包含 A 的累积最小值。
如果 A 是矩阵,则 M 是具有相同大小和类型的矩阵,并且包含 A 的每列中的累积最小值。
M = cummin(A,dim) 返回沿维度 dim 的累积最小值。例如,如果 A 是矩阵,则 cummin(A,2) 沿 A 的各行返回累积最小值。
M = cummin(___,direction) 可在上述任一语法的基础上指定计算方向。例如,cummin(A,2,"reverse") 通过从尾到头计算 A 的第二个维度返回 A 的累积最小值。
M = cummin(___,nanflag) 指定忽略还是包括 A 中的 NaN 值。例如,cummin(A,"includenan") 在计算每个最小值时包含 NaN 值。默认情况下,cummin 忽略 NaN 值。
A — 输入数组, 向量 | 矩阵
dim — 沿其运算的维度, 正整数标量
direction — 累积方向, "forward" (默认) | "reverse"
nanflag — 缺失值条件, "omitmissing" (默认) | "omitnan" | "includemissing" | "includenan"
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import numpy as np
import sympy as sp
def cumulative_min_symbolic(input_str):
"""
处理符号累积和的入口函数,解析输入参数并调用核心计算函数。
参数:
input_expr: 输入的表达式,可以是矩阵、列表或包含矩阵及参数的元组
返回:
累积和的结果或错误信息
"""
try:
input_expr = sp.sympify(input_str)
result = None
def cummin(A, dim=None, direction='forward', nanflag='propagate'):
"""
MATLAB cummin函数的NumPy实现
参数:
A: 输入数组
dim: 计算累积最小值的维度,默认为第一个非单一维度
direction: 累积方向,'forward'(默认)或'backward'
nanflag: NaN处理方式,'propagate'(默认)或'omitnan'
返回:
与A形状相同的数组,包含累积最小值
"""
A = np.asarray(A)
# 处理dim参数(默认行为:选择第一个非单一维度)
if dim is None:
if A.size == 0:
dim = 0
else:
dim = next((i for i, s in enumerate(A.shape) if s > 1), 0)
# 处理direction参数
if direction == 'backward':
# 对于后向累积,先反转数组,计算前向累积,再反转回来
slices = [slice(None)] * A.ndim
slices[dim] = slice(None, None, -1)
A_reversed = A[tuple(slices)]
if nanflag == 'omitnan':
# 对每个切片单独处理NaN
result = np.apply_along_axis(_cummin_omitnan, dim, A_reversed)
else:
result = np.minimum.accumulate(A_reversed, axis=dim)
# 反转结果恢复原始顺序
result = result[tuple(slices)]
return result
else: # forward
if nanflag == 'omitnan':
# 对每个切片单独处理NaN
return np.apply_along_axis(_cummin_omitnan, dim, A)
else:
return np.minimum.accumulate(A, axis=dim)
def _cummin_omitnan(arr):
"""辅助函数:处理包含NaN的数组,忽略NaN计算累积最小值"""
mask = np.isnan(arr)
if np.all(mask):
return np.full_like(arr, np.nan)
# 找到第一个非NaN值
first_valid = next((i for i, x in enumerate(arr) if not np.isnan(x)), 0)
result = np.full_like(arr, np.nan)
result[first_valid] = arr[first_valid]
# 计算剩余位置的累积最小值
for i in range(first_valid + 1, len(arr)):
if not np.isnan(arr[i]):
result[i] = min(result[i - 1], arr[i])
else:
result[i] = result[i - 1]
return result
# 解析输入表达式
if isinstance(input_expr, tuple):
if not isinstance(input_expr[0], list):
raise ValueError(f"输入错误:{input_str}")
else:
A = sp.Array(input_expr[0])
params = input_expr[1:]
dim = None # 默认让函数内部处理
direction = 'forward'
nanflag = 'includenan'
# 解析参数
for param in params:
if isinstance(param, (int, sp.Integer)):
dim = int(param) - 1
elif str(param).lower() in ['forward', 'reverse']:
direction = str(param).lower()
elif str(param).lower() in ['includenan', 'omitnan']:
nanflag = str(param).lower()
# 参数校验
if dim is not None and dim not in [1, 2]:
return f"错误: 维度参数 dim 必须为 1 或 2,当前为 {dim}"
if direction not in ['forward', 'reverse']:
return f"错误: 方向参数 direction 必须为 'forward' 或 'reverse',当前为 {direction}"
if nanflag not in ['includenan', 'omitnan']:
return f"错误: nanflag 参数无效,当前为 {nanflag}"
# 调用核心计算函数
np_a = np.asarray(A.tolist(), dtype=float)
result = cummin(np_a, dim=dim, direction=direction, nanflag=nanflag)
else:
# 输入为单一矩阵
if not isinstance(input_expr, list):
raise ValueError(f"输入错误:{input_str}")
else:
A = sp.Array(input_expr)
np_a = np.asarray(A.tolist(), dtype=float)
result = cummin(np_a)
return result
except Exception as e:
return f"错误: {e}"
# 示例用法
if __name__ == "__main__":
# 创建示例数组
# 测试不同参数组合
# 默认参数
print(cumulative_min_symbolic("[[3,5,2],[1,6,3],[7,8,1]]"))
# [[3. 5. 2.]
# [1. 5. 2.]
# [1. 5. 1.]]
# 指定维度
print(cumulative_min_symbolic("[[3,5,2],[1,6,3],[7,8,1]],2"))
# [[3. 3. 2.]
# [1. 1. 1.]
# [7. 7. 1.]]
# 后向累积
print(cumulative_min_symbolic("[[3,5,nan,4],[2,6,2,9],[1,3,0,nan]],backward"))
# [[ 3. 5. nan 4.]
# [ 2. 5. nan 4.]
# [ 1. 3. nan nan]]
# 忽略NaN
print(cumulative_min_symbolic("[[3,5,nan,4],[2,6,2,9],[1,3,0,nan]],includenan"))
# [[ 3. 5. nan 4.]
# [ 2. 5. nan 4.]
# [ 1. 3. nan nan]]
# 指定维度
print(cumulative_min_symbolic("[[[5, 3, 7],[2, 6, 1],[4, 2, 3]],[[8, 1, 5],[9, 4, 6],[3, nan, 2]]],2"))
# [[[ 5. 3. 7.]
# [ 2. 3. 1.]
# [ 2. 2. 1.]]
#
# [[ 8. 1. 5.]
# [ 8. 1. 5.]
# [ 3. nan 2.]]]
累积乘积
B = cumprod(A) 返回从 A 中大小不等于 1 的第一个数组维度的开头开始的 A 的累积乘积. 输出 B 的大小与 A 相同.
如果 A 是向量,则 cumprod(A) 返回一个包含 A 元素累积乘积的向量.
如果 A 是矩阵,则 cumprod(A) 返回一个包含 A 每一列累积乘积的矩阵.
B = cumprod(A,dim) 返回沿维度 dim 的累积乘积. 例如如果 A 是矩阵, 则 cumprod(A,2) 返回每行的累积乘积.
B = cumprod(___,direction) 使用任何先前的语法指定方向. 例如,cumprod(A,2,'reverse') 通过从第二维度的末尾到开头来返回 A 行内的累积乘积.
B = cumprod(___,nanflag) 指定是否在计算中包含或省略 NaN 值, 适用于任何先前的语法. cumprod(A,'includenan') 在计算中包含所有 NaN 值, 而 cumprod(A,'omitnan') 则忽略它们.
A — 输入数组,向量,矩阵.
dim — 沿正整数标量进行运算的维度, 只支持1(默认)或2.
direction — 累积方向, 'forward'(默认)| 'reverse'
nanflag — NaN 条件,'includenan'(默认)| 'omitnan'
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cumulative_product_symbolic(input_str):
"""
对标MATLAB的cumprod函数,计算多维数组的累积乘积
参数:
input_str: 输入的字符串,表示数组或包含参数的元组
返回:
累积乘积结果或错误信息
"""
try:
expr = sp.sympify(input_str)
error = False
result = None
# 处理输入元组
if isinstance(expr, tuple):
elements = list(expr)
sp_array = sp.Array(elements[0]) if isinstance(elements[0], list) else None
if sp_array is None:
return f"输入错误: 无法解析数组 {elements[0]}"
params = elements[1:]
dim = None
direction = 'forward'
nanflag = 'includenan'
# 解析参数
for param in params:
if isinstance(param, (int, sp.Integer)):
dim = int(param)
elif str(param).lower() in ['forward', 'reverse']:
direction = str(param).lower()
elif str(param).lower() in ['includenan', 'omitnan']:
nanflag = str(param).lower()
# 将SymPy数组转换为NumPy数组
np_arr = np.asarray(sp_array, dtype=float)
# 处理NaN
if nanflag == 'omitnan':
# 对于多维数组,不能直接删除NaN,转为1
np_arr = np.nan_to_num(np_arr, nan=1.0)
# 处理方向参数
if direction == 'reverse':
# 反转数组
if dim is not None:
# 沿指定维度反转
np_arr = np.flip(np_arr, axis=dim - 1)
else:
# 默认沿第一个非单例维度
dim = next((i + 1 for i, s in enumerate(np_arr.shape) if s > 1), 1)
np_arr = np.flip(np_arr, axis=dim - 1)
# 处理维度参数 (MATLAB风格转为Python风格)
axis = dim - 1 if dim is not None else None
# 计算累积乘积
result = np.cumprod(np_arr, axis=axis)
# 如果是反向累积,需要再反转回来
if direction == 'reverse':
if dim is not None:
result = np.flip(result, axis=dim - 1)
else:
result = np.flip(result, axis=axis)
else:
# 处理简单数组输入
sp_array = sp.Array(expr) if isinstance(expr, list) else None
if sp_array is None:
return f"输入错误: {input_str}"
np_arr = np.asarray(sp_array, dtype=float)
result = np.cumprod(np_arr)
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {str(e)}"
# 测试用例
if __name__ == "__main__":
# 测试用例1: 一维数组,默认参数
print("测试1: 一维数组,默认参数")
input1 = '[1, 2, 3, 4]'
print(f"输入: {input1}")
print(f"输出: {cumulative_product_symbolic(input1)}")
print()
# 输出: [ 1. 2. 6. 24.]
# 测试用例2: 二维数组,指定维度2
print("测试2: 二维数组,指定维度2")
input2 = '([[1, 2, 3], [4, 5, 6]], 2)'
print(f"输入: {input2}")
print(f"输出: {cumulative_product_symbolic(input2)}")
print()
# 输出: [[ 1. 2. 6.]
# [ 4. 20. 120.]]
# 测试用例3: 二维数组,反向累积
print("测试3: 二维数组,反向累积")
input3 = '([[1, 2, 3], [4, 5, 6]], "reverse")'
print(f"输入: {input3}")
print(f"输出: {cumulative_product_symbolic(input3)}")
print()
# 输出: [[ 4. 10. 18.]
# [ 4. 5. 6.]]
# 测试用例4: 二维数组,忽略NaN
print("测试4: 二维数组,忽略NaN")
input4 = '([[1, nan, 3], [4, 5, nan]], "omitnan")'
print(f"输入: {input4}")
print(f"输出: {cumulative_product_symbolic(input4)}")
print()
# 输出: [ 1. 1. 3. 12. 60. 60.]
# 测试用例5: 三维数组,指定维度3
print("测试5: 三维数组,指定维度3")
input5 = '([[[1, 2], [3, 4]], [[5, 6], [7, 8]]], 3)'
print(f"输入: {input5}")
print(f"输出: {cumulative_product_symbolic(input5)}")
print()
# [[[ 1. 2.]
# [ 3. 12.]]
#
# [[ 5. 30.]
# [ 7. 56.]]]
# 测试用例6: 三维数组,反向累积
print("测试6: 三维数组,反向累积")
input6 = '([[[1, 2], [3, 4]], [[5, 6], [7, 8]]], 2, "reverse")'
print(f"输入: {input6}")
print(f"输出: {cumulative_product_symbolic(input6)}")
print()
# [[[ 3. 8.]
# [ 3. 4.]]
#
# [[35. 48.]
# [ 7. 8.]]]
累积和
B = cumsum(A) 返回从 A 中大小不等于 1 的第一个数组维度的开头开始的 A 的累积和.
如果 A 是向量, 则 B 是包含 A 累积和的相同大小的向量.
如果 A 是矩阵, 则 B 是包含 A 每一列累积和的相同大小的矩阵.
B = cumsum(A,dim) 返回维度 dim 上元素的累积和. 例如如果 A 是矩阵, 则 cumsum(A,2) 返回沿 A 行计算的累积和.
B = cumsum(___,direction) 指定任何先前语法的方向. 例如, cumsum(A,2,"reverse") 通过从第二维的末尾到开头计算,返回 A 行内的累积和.
B = cumsum(___,nanflag) 指定是否在 A 中包含或忽略 NaN 值. 例如, cumsum(A,"omitnan") 在计算每个和时忽略 NaN 值. 默认情况下, cumsum 包含 NaN 值.
A — 输入数组,向量,矩阵.
dim — 沿正整数标量进行运算的维度, 只支持1(默认)或2.
direction — 累积方向, 'forward'(默认)| 'reverse'
nanflag — NaN 条件,"includemissing" (默认) | "includenan" | "omitmissing" | "omitnan"
“includemissing” 或 “includenan” — 计算累积和时包含 A 中的 NaN 值. 一旦遇到 A 中的第一个 NaN 值, B 中的元素即为 NaN. “includemissing” 和 “includenan” 具有相同的行为.
“omitmissing” 或 “omitnan” — 计算累积和时忽略 A 中的 NaN 值. 如果 A 具有连续的前导 NaN 值, 则 B 中的相应元素为 0. “omitmissing” 和 “omitnan” 具有相同的行为.
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cumulative_sum_symbolic(input_str):
try:
input_expr = sp.sympify(input_str)
result = None
def cumsum_matlike(a, dim=None, direction='forward', nanflag='includenan'):
arr = np.asarray(a, dtype=float)
# 处理NaN值
if nanflag == 'omitnan':
arr = np.where(np.isnan(arr), 0, arr)
# 确定累积维度 (MATLAB默认按列累积,即dim=1)
if dim is None:
# 默认按列累积 (MATLAB行为)
axis = 0 if arr.ndim > 1 else 0
else:
# 将MATLAB维度转换为NumPy维度
axis = dim - 1
# 根据方向进行累积求和
if direction == 'reverse':
# 反转数组,进行正向累积,然后反转回原顺序
reversed_arr = np.flip(arr, axis=axis)
cum_result = np.cumsum(reversed_arr, axis=axis)
result = np.flip(cum_result, axis=axis)
else: # 'forward'
result = np.cumsum(arr, axis=axis)
return result
# 解析输入表达式
if isinstance(input_expr, tuple):
A = sp.Array(input_expr[0])
params = input_expr[1:]
dim = None # 默认让函数内部处理
direction = 'forward'
nanflag = 'includenan'
# 解析参数
for param in params:
if isinstance(param, (int, sp.Integer)):
dim = int(param)
elif str(param).lower() in ['forward', 'reverse']:
direction = str(param).lower()
elif str(param).lower() in ['includenan', 'omitnan']:
nanflag = str(param).lower()
# 参数校验
if dim is not None and dim not in [1, 2]:
return f"错误: 维度参数 dim 必须为 1 或 2,当前为 {dim}"
if direction not in ['forward', 'reverse']:
return f"错误: 方向参数 direction 必须为 'forward' 或 'reverse',当前为 {direction}"
if nanflag not in ['includenan', 'omitnan']:
return f"错误: nanflag 参数无效,当前为 {nanflag}"
# 调用核心计算函数
np_a = np.asarray(A.tolist(), dtype=float)
result = cumsum_matlike(np_a, dim=dim, direction=direction, nanflag=nanflag)
else:
# 输入为单一矩阵
A = sp.Array(input_expr)
np_a = np.asarray(A.tolist(), dtype=float)
result = cumsum_matlike(np_a)
return result # 转换为列表格式输出
except Exception as e:
return f"错误: {e}"
# 测试修正后的代码
print(cumulative_sum_symbolic("[[3,5,nan,4],[2,6,nan,9],[1,3,5,nan]],omitnan"))
# 输出:
# [[ 3. 5. 0. 4.]
# [ 5. 11. 0. 13.]
# [ 6. 14. 5. 13.]]
符号向量场的旋度
c = curl(V) 返回向量场 V 相对于由 V 中的符号变量构造的默认向量的旋度.
通常情况下,向量场的旋度是对给定的函数关于变量 x,y 和 z 的偏导数而得到的,而不是针对特定的数值进行计算的.
V — 三维符号向量场, 符号标量变量的向量
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import sympy.physics.vector as svt
def curl_vector_field(input_str):
"""
计算矢量场的旋度,对标MATLAB的curl函数。
参数:
input_str (str): 矢量场的三个分量的字符串表达式,例如 "[x*y, y*z, z*x]"
返回:
tuple: 旋度的三个分量的SymPy表达式,或错误信息字符串。
"""
try:
F_expr = sp.sympify(input_str)
# 检查输入是否为三个分量的列表
if not isinstance(F_expr, tuple) or len(F_expr) != 3:
return "错误: 输入必须是包含三个分量的列表,例如 '[x*y, y*z, z*x]'"
# 创建一个参考坐标系
N = svt.ReferenceFrame('N')
# 将表达式中的符号变量替换为 N[0]、N[1] 和 N[2]
F_expr_substituted = [expr.subs({'x': N[0], 'y': N[1], 'z': N[2]}) for expr in F_expr]
# 将表达式转换为矢量场
F = F_expr_substituted[0] * N.x + F_expr_substituted[1] * N.y + F_expr_substituted[2] * N.z
# 计算矢量场的旋度
result = svt.curl(F, N)
# 计算每个分量的值
# 将 result_x 中的 N.x 替换为 x,N.y 替换为 y,N.z 替换为 z
result = result.subs({N[0]: sp.symbols('x'), N[1]: sp.symbols('y'), N[2]: sp.symbols('z')})
result_x = result.dot(N.x)
result_y = result.dot(N.y)
result_z = result.dot(N.z)
# 使用 f-string 组成结果字符串并返回
return result_x, result_y, result_z
except Exception as e:
return f"错误: {e}"
if __name__ == "__main__":
# 示例输入
input_str = "(x*y, y*z, z*x)"
print(f"输入矢量场: {input_str}")
# 计算旋度
result = curl_vector_field(input_str)
# 输出结果
if isinstance(result, tuple):
print("\n旋度计算结果:")
print(f"x分量: {result[0]}")
print(f"y分量: {result[1]}")
print(f"z分量: {result[2]}")
# x分量: -y
# y分量: -z
# z分量: -x
else:
print(result)
# 另一个示例:无旋场
input_str2 = "(y, x, 0)"
print(f"\n输入矢量场: {input_str2}")
result2 = curl_vector_field(input_str2)
if isinstance(result2, tuple):
print("\n旋度计算结果:")
print(f"x分量: {result2[0]}")
print(f"y分量: {result2[1]}")
print(f"z分量: {result2[2]}")
# x分量: 0
# y分量: 0
# z分量: 0
else:
print(result2)
输入角的余割(以弧度为单位)
Y = csc(X) 返回X的元素的余割.csc函数按元素处理数组.该函数同时接受实数和复数输入.
对于X的实数值,csc(X)返回区间[-∞, - 1] 和 [1, ∞]内的实数值.
对于X的复数值,csc(X)返回复数值.
X — 输入角(以弧度为单位), 标量,向量,矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cosine_theta_value(input_str):
"""
计算输入表达式或矩阵的余割值 (csc)
参数:
input_str: 输入的字符串表达式,可以是矩阵、数值或符号表达式
返回:
计算结果 (浮点数或矩阵),如果输入无效则返回错误信息字符串
"""
try:
# 将输入字符串解析为 SymPy 表达式
expr = sp.sympify(input_str)
error = False
result = None
# 处理元组类型输入 (不支持)
if isinstance(expr, tuple):
error = True
# 处理矩阵类型输入
# 处理数值或符号表达式
elif expr.is_number:
z = complex(expr)
result = 1 / np.sin(z)
elif expr.free_symbols:
result = sp.csc(expr).evalf() # 计算余割并转为浮点数
else:
error = True
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}" # 返回异常信息
def main():
"""示例入口程序,演示不同输入情况下的行为"""
test_inputs = [
"pi/2", # (1+0j)
"2", # (1.0997501702946164+0j)
"x", # csc(x)
]
for inp in test_inputs:
print(f"输入: {inp}")
result = cosine_theta_value(inp)
print(f"结果: {result}\n{'-' * 30}")
if __name__ == "__main__":
main()
输入角的余割(以度为单位)
Y = cscd(X) 返回X元素的余割,以度为单位表示.
X — 角度(度),标量值,向量,矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cosine_theta_degree(input_str):
"""
计算输入表达式(矩阵、数值或符号)的余割(csc)值,角度以度数表示。
参数:
input_str: 输入的字符串,可以是矩阵、数值或符号表达式。
返回:
计算结果(矩阵、数值或符号表达式)或错误信息字符串。
"""
try:
# 将输入字符串转换为SymPy表达式
expr = sp.sympify(input_str)
error = False
result = None
# 处理元组输入(视为无效)
if isinstance(expr, tuple):
error = True
# 处理矩阵输入
# 处理数值或符号表达式
elif expr.is_number:
# 数值处理:将输入转换为NumPy数组(支持标量和向量)
z = complex(expr)
# 将角度转换为弧度
x_rad = z * np.pi / 180
# 计算正弦值
sin_values = np.sin(x_rad)
# 计算余割值(1/sin(x))
result = 1 / sin_values
elif expr.free_symbols:
result = sp.csc(expr * sp.pi / 180)
# 其他类型视为错误
else:
error = True
# 根据错误标志返回结果或错误信息
return result if not error else f"输入错误: {input_str}"
except Exception as e:
return f"错误: {e}"
if __name__ == '__main__':
# 示例1:计算30度的余割(应返回2.0)
input1 = '30'
result1 = cosine_theta_degree(input1)
print(f"输入: {input1}\n结果: {result1}\n")
# 结果: (2.0000000000000004+0j)
# 示例2:符号计算(返回符号表达式)
input2 = 'x'
result2 = cosine_theta_degree(input2)
print(f"输入: {input2}\n结果: {result2}\n")
# 结果: csc(pi*x/180)
双曲余割
Y = csch(X) 返回X的元素的双曲余割.csch函数按元素处理数组.该函数同时接受实数和复数输入.所有的角度都以弧度表示.
X — 角度(度),标量值,向量,矩阵
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
def cosine_theta_hyperbolic(input_str):
"""
对输入的字符串表达式进行处理,计算双曲余割值。
参数:
input_str: 输入的字符串表达式。
返回:
如果输入有效,返回计算结果;否则返回错误信息。
"""
try:
# 将输入的字符串转换为 SymPy 表达式
expr = sp.sympify(input_str)
# 初始化错误标志和结果变量
error = False
result = None
# 检查表达式是否为元组,如果是则标记为错误
if isinstance(expr, tuple):
error = True
# 检查表达式是否为数字或包含自由符号
elif expr.is_number or expr.free_symbols:
# 若为数字或包含自由符号,对表达式应用双曲余割函数并求值
result = sp.csch(expr).evalf()
else:
# 其他情况标记为错误
error = True
# 如果没有错误,返回计算结果;否则返回错误信息
return result if not error else f"输入错误: {input_str}"
except Exception as e:
# 若处理过程中出现异常,返回错误信息
return f"错误:{e}"
def main():
"""
主程序,用于测试 cosine_theta_hyperbolic 函数。
"""
# 测试输入:单个数字
input1 = "2"
result1 = cosine_theta_hyperbolic(input1)
print(f"输入: {input1}, 结果: {result1}")
# 结果: 0.275720564771783
# 测试输入:包含符号的表达式
x = sp.Symbol('x')
input3 = str(x)
result3 = cosine_theta_hyperbolic(input3)
print(f"输入: {input3}, 结果: {result3}")
# 结果: csch(x)
if __name__ == "__main__":
main()
累积梯形数值积分
Q = cumtrapz(Y) 通过梯形法按单位间距计算 Y 的近似累积积分. Y 的大小确定求积分所沿用的维度.
如果 Y 是向量, 则 cumtrapz(Y) 是 Y 的累积积分.
如果 Y 是矩阵, 则 cumtrapz(Y) 是每一列的累积积分.
Q = cumtrapz(X,Y) 根据 X 指定的坐标或标量间距对 Y 进行积分.
如果 X 是坐标向量, 则 length(X) 必须等于 Y 的大小不等于 1 的第一个维度的大小.
如果 X 是标量间距, 则 cumtrapz(X,Y) 等于 X*cumtrapz(Y).
Q = cumtrapz(___,dim) 使用上述任意语法沿维度dim求积分. 必须指定Y,也可以指定X. 如果指定X,则它可以是长度等于 size(Y,dim) 的标量或向量. 例如, 如果Y是矩阵, 则 cumtrapz(X,Y,2) 对 Y 的每一行进行累积积分.
Y — 数值数据, 向量, 矩阵, 符号表达式
X — 点间距, 1 (默认),均匀的标量间距,坐标向量
dim — 沿其运算的维度, 正整数标量 (二维矩阵只有列或行,dim值为1或2)
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
from scipy import integrate
def cumulative_integrate_trapezoid(input_str):
"""
对标MATLAB的cumtrapz函数,实现累积梯形积分
支持以下输入格式:
1. 单个数组: cumulative_integrate_trapezoid('[1,2,3]')
2. 元组(x,y): cumulative_integrate_trapezoid('([1,2,3], [4,5,6])')
3. 元组(x,y,axis): cumulative_integrate_trapezoid('([1,2,3], [[4,5,6],[7,8,9]], 2)')
4. 符号表达式: cumulative_integrate_trapezoid('([1,2,3], x**2)')
参数:
input_str: 表示输入的字符串
返回:
积分结果数组或错误信息
"""
try:
expr = sp.sympify(input_str)
error = False
result = None
def symbolic_cumtrapz(y_expr, x, x_vals):
cumulative_integral = [0.0] # 初始为0
for i in range(1, len(x_vals)):
x0 = x_vals[i - 1]
x1 = x_vals[i]
y0 = y_expr.subs(x, x0)
y1 = y_expr.subs(x, x1)
integral_segment = (y0 + y1) * (x1 - x0) / 2
current = cumulative_integral[-1] + integral_segment
cumulative_integral.append(current)
return cumulative_integral
if isinstance(expr, tuple) and len(expr) > 2:
x = sp.Matrix(expr[0]) if isinstance(expr[0], list) else None
y = sp.Matrix(expr[1]) if isinstance(expr[1], list) else None
if x is not None and y is not None and expr[2] in [1, 2]:
axis = expr[2] - 1
n_x = np.ravel(np.array(x, dtype=float))
n_y = np.array(y, dtype=float)
result = integrate.cumtrapz(n_y, n_x, axis=axis, initial=0)
else:
error = True
elif isinstance(expr, tuple) and len(expr) == 2:
x = sp.Matrix(expr[0]) if isinstance(expr[0], list) else None
y = sp.Matrix(expr[1]) if isinstance(expr[1], list) else None
if x is not None and y is not None:
n_x = np.ravel(np.array(x, dtype=float))
n_y = np.array(y, dtype=float)
result = integrate.cumtrapz(n_y, n_x, initial=0)
elif x is not None and expr[1].free_symbols:
y_expr = expr[1]
y_symbol = list(y_expr.free_symbols)[0]
x_vals = np.ravel(np.array(x, dtype=float))
result = symbolic_cumtrapz(y_expr, y_symbol, x_vals)
else:
error = True
elif isinstance(expr, list):
x = sp.Matrix(expr)
n_x = np.ravel(np.array(x, dtype=float))
result = integrate.cumtrapz(n_x, initial=0)
else:
error = True
if error:
return f"输入错误: {input_str}"
else:
# 转换为SymPy矩阵
if isinstance(result, np.ndarray):
result = result.tolist()
res_matrix = sp.Matrix(result)
if res_matrix.shape[1] == 1:
return res_matrix.T.tolist()[0] # 返回向量列表
else:
return res_matrix
except Exception as e:
return f"错误: {e}"
def main():
"""
主函数,用于演示 cumulative_integrate_trapezoid 函数的使用。
"""
# 示例 1: 输入为数据点间距为 1 的向量的累积积分
input_str1 = "[1,4,9,16,25]"
result1 = cumulative_integrate_trapezoid(input_str1)
print(f"输入: {input_str1}\n结果: {result1}\n")
# 结果: [0, 2.50000000000000, 9.00000000000000, 21.5000000000000, 42.0000000000000]
# 示例 2: 输入为计算数据点间距均匀但不等于 1 的向量的累积积分
input_str2 = "[0,pi/5,2*pi/5,3*pi/5,4*pi/5,pi],sin(x)"
result2 = cumulative_integrate_trapezoid(input_str2)
print(f"输入: {input_str2}\n结果: {result2}\n")
# 结果: [0, 0.184658183049046, 0.668099582572247, 1.26566601552056, 1.74910741504376, 1.93376559809281]
# 示例 3: 输入为对具有非均匀数据间距的矩阵的行进行累积积分
input_str3 = "[1,2.5,7,10],[[5.2,7.7,9.6,13.2],[4.8,7,10.5,14.5],[4.9,6.5,10.2,13.8]],2"
result3 = cumulative_integrate_trapezoid(input_str3)
print(f"输入: {input_str3}\n结果: {result3}\n")
# 结果: Matrix([[0, 9.67500000000000, 48.6000000000000, 82.8000000000000],
# [0, 8.85000000000000, 48.2250000000000, 85.7250000000000],
# [0, 8.55000000000000, 46.1250000000000, 82.1250000000000]])
if __name__ == "__main__":
main()
其列周期性重复的矩阵
A = cycol(n,k)返回具有周期性重复列的 n×n 矩阵,其中一个周期由 randn(n,k) 定义的列构成.因此,矩阵 A 的秩不能超过k, k必须是标量. 参量k是标量, 默认值为 round(n/4),它不需要整除 n.
n,k - 输入, 标量
# Copyright 2025 小塔立软件有限公司及其旗下网站:www.qikjik.com
# Licensed under the MIT License.
import sympy as sp
import numpy as np
def cycol_matrix(input_str):
"""
根据输入的字符串生成循环矩阵。输入应为形如 "(n, k)" 的字符串,
其中 n 和 k 是正整数,分别表示矩阵的行数和列数。
参数:
input_str (str): 格式为 "(n, k)" 的字符串
返回:
sp.Matrix: 生成的循环矩阵,或错误信息字符串
"""
try:
# 将输入字符串转换为SymPy表达式
expr = sp.sympify(input_str)
error = False
result = None
# 检查输入是否为包含两个正整数的元组
if (isinstance(expr, tuple) and # SymPy元组类型检查
len(expr) == 2 and # 必须包含两个元素
all(arg.is_integer for arg in expr) and # 两个元素都必须是整数
int(expr[0]) > 0 and # n必须为正整数
int(expr[1]) > 0): # k必须为正整数
n = int(expr[0])
k = int(expr[1])
def generate_cycol_matrix(n, k):
"""
生成n行k列的循环矩阵,每列是前一列的循环下移
参数:
n (int): 行数
k (int): 列数
返回:
np.ndarray: 生成的循环矩阵
"""
base_col = np.arange(1, n + 1) # 生成基础列 [1, 2, ..., n]
# 生成k个循环移位列,i列是基础列下移i次
columns = [np.roll(base_col, shift=i) for i in range(k)]
return np.column_stack(columns) # 将列合并为矩阵
result = generate_cycol_matrix(n, k)
else:
error = True
if error:
return f"输入错误: 需要两个正整数的元组,例如'(3,4)'。收到:{input_str}"
else:
return sp.Matrix(result) # 转换为SymPy矩阵返回
except Exception as e:
return f"错误: {str(e)}"
if __name__ == "__main__":
# 示例用法
print("正确输入示例:")
test_cases = [
"(3, 4)",
# Matrix([[1, 3, 2, 1],
# [2, 1, 3, 2],
# [3, 2, 1, 3]])
"(6, 3)",
# Matrix([[1, 6, 5],
# [2, 1, 6],
# [3, 2, 1],
# [4, 3, 2],
# [5, 4, 3],
# [6, 5, 4]])
"(4, 6)",
# Matrix([[1, 4, 3, 2, 1, 4],
# [2, 1, 4, 3, 2, 1],
# [3, 2, 1, 4, 3, 2],
# [4, 3, 2, 1, 4, 3]])
]
for case in test_cases:
print(f"\n输入: {case}")
print("输出矩阵:")
print(cycol_matrix(case))