「両端固定梁の任意位置の集中荷重のモーメントの計算方法を教えて下さい。」をAI先生に聞きました。sympyのソースコードで。 

# (本日の)ChatGPT先生へ
#### 質問リスト
・質問リストの追番は無視して下さい。１個ずつです。途中の回答表示は省略しています。
```
# 質問リスト
1. 両端固定梁の任意位置の集中荷重のモーメントの計算方法を教えて下さい。
2. 図解で。
3. 端部のモーメントが負になるのは、どうしてですか。
4. 計算方法がsympy のソースコードで教えて下さい。
5. 端部の公式の計算をsympy のソースコードで教えて下さい。
6. 追加します。
7. 追加します。
8. 対応お願いします。
9. 必要です。
10. 必要です。
11. 私の質問をMarkdown形式でリスト化して出力して。Markdown形式でリストからアスタリスクは削除して。1行目に、# 質問リスト の文字を出力して。最後の質問も追加して下さい。追番を追加して下さい。Markdown形式で。
```
画像が生成されました。
![4cfdd049-53ea-4d2d-9d19-754bfb66507a.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/109698/43207f9f-276e-4bb7-bdc3-a0f1b1fbf14a.png)

端部のモーメントが負になるのは、どうしてですか。
>端部のモーメントが負になる理由は、**固定端に生じる回転を抑えるために生じる「逆向きの曲げモーメント」**によるものです。以下でわかりやすく説明します。
...
【符号の意味】
・負のモーメント（下向きにたわむ方向に反するモーメント）は、断面において上側が圧縮・下側が引張の状態です（通常の符号規則に従えば）。
・荷重が中央や任意の位置にあると、中央付近で上に凸の変形が起こるので、それを抑えるように端部では上向きに持ち上げる（＝上側圧縮）モーメントが必要です。
...
>以下は、SymPyを使って両端固定梁における任意位置の集中荷重による**端部モーメント（MA, MB）**を求めるソースコードです：
```python
import sympy as sp

# 記号の定義
P, a, b, L = sp.symbols('P a b L', positive=True)

# MA と MB の公式（両端固定梁の端モーメント）
MA = -P * b**2 * (3*a + b) / L**3
MB = -P * a**2 * (3*b + a) / L**3

# 表示
sp.pprint(sp.Eq(sp.Symbol('M_A'), MA))
sp.pprint(sp.Eq(sp.Symbol('M_B'), MB))
```
端部の公式の計算をsympy のソースコードで教えて下さい。
>了解しました。以下に、両端固定梁の端部モーメント（MA, MB）の公式をSymPyを使って力学的に導出するコードを示します。これは、力の釣り合いと変位条件（両端の回転ゼロ）から式を立てて解く方法です。
```python
import sympy as sp

# 記号の定義
x, a, L, P, MA, MB = sp.symbols('x a L P MA MB')
b = L - a
RA, RB = sp.symbols('RA RB')

# モーメント関数の分割（部材全体を2区間に分ける）
# モーメント M(x) は力の積分で定義される（符号に注意）

# 左側（0 <= x < a）
Mx1 = MA + RA * x

# 右側（a <= x <= L）
Mx2 = MA + RA * x - P * (x - a)

# たわみ関数 EI*y'' = M(x)
# 2回積分して EI*y(x) を求める（積分定数は C1, C2）
C1, C2, C3, C4 = sp.symbols('C1 C2 C3 C4')

# 左側たわみ（0 <= x < a）
theta1 = sp.integrate(Mx1, x) + C1
y1 = sp.integrate(theta1, x) + C2

# 右側たわみ（a <= x <= L）
theta2 = sp.integrate(Mx2, x) + C3
y2 = sp.integrate(theta2, x) + C4

# 条件設定（固定端条件 + たわみと角度の連続）
eqs = [
    y1.subs(x, 0),                 # y(0) = 0
    theta1.subs(x, 0),             # θ(0) = 0
    y2.subs(x, L),                 # y(L) = 0
    theta2.subs(x, L),             # θ(L) = 0
    y1.subs(x, a) - y2.subs(x, a), # たわみの連続
    theta1.subs(x, a) - theta2.subs(x, a), # 角度の連続
    RA + RB - P,                   # 垂直力の釣り合い
    MA + MB + RA * a - P * (a)     # モーメントの釣り合い（任意点で）
]

# 未知数
unknowns = [RA, RB, MA, MB, C1, C2, C3, C4]

# 方程式を解く
sol = sp.solve(eqs, unknowns, simplify=True)

# 出力
sp.pprint(sp.Eq(sp.Symbol('M_A'), sol[MA]))
sp.pprint(sp.Eq(sp.Symbol('M_B'), sol[MB]))
```
#### 【SymPyでの導出コード】
```python
import sympy as sp

# 記号の定義
x, a, L, P, MA, MB = sp.symbols('x a L P MA MB')
b = L - a
RA, RB = sp.symbols('RA RB')

# モーメント関数の分割（部材全体を2区間に分ける）
# モーメント M(x) は力の積分で定義される（符号に注意）

# 左側（0 <= x < a）
Mx1 = MA + RA * x

# 右側（a <= x <= L）
Mx2 = MA + RA * x - P * (x - a)

# たわみ関数 EI*y'' = M(x)
# 2回積分して EI*y(x) を求める（積分定数は C1, C2）
C1, C2, C3, C4 = sp.symbols('C1 C2 C3 C4')

# 左側たわみ（0 <= x < a）
theta1 = sp.integrate(Mx1, x) + C1
y1 = sp.integrate(theta1, x) + C2

# 右側たわみ（a <= x <= L）
theta2 = sp.integrate(Mx2, x) + C3
y2 = sp.integrate(theta2, x) + C4

# 条件設定（固定端条件 + たわみと角度の連続）
eqs = [
    y1.subs(x, 0),                 # y(0) = 0
    theta1.subs(x, 0),             # θ(0) = 0
    y2.subs(x, L),                 # y(L) = 0
    theta2.subs(x, L),             # θ(L) = 0
    y1.subs(x, a) - y2.subs(x, a), # たわみの連続
    theta1.subs(x, a) - theta2.subs(x, a), # 角度の連続
    RA + RB - P,                   # 垂直力の釣り合い
    MA + MB + RA * a - P * (a)     # モーメントの釣り合い（任意点で）
]

# 未知数
unknowns = [RA, RB, MA, MB, C1, C2, C3, C4]

# 方程式を解く
sol = sp.solve(eqs, unknowns, simplify=True)

# 出力
sp.pprint(sp.Eq(sp.Symbol('M_A'), sol[MA]))
sp.pprint(sp.Eq(sp.Symbol('M_B'), sol[MB]))
```

#### 【完全なSymPyコード（モーメント図・たわみ曲線）】
```python
import sympy as sp
import numpy as np
import matplotlib.pyplot as plt

# 記号定義
x, a, L, P = sp.symbols('x a L P', real=True, positive=True)
b = L - a
EI = sp.Symbol('EI', positive=True)

# 端部モーメント公式
MA = -P * b**2 * (3*a + b) / L**3
MB = -P * a**2 * (3*b + a) / L**3

# 反力
RA = (P * b**2 * (3*a + b)) / L**3 + (P * a * b) / L
RB = P - RA

# モーメント関数（区間で分ける）
Mx_left = MA + RA * x
Mx_right = MA + RA * x - P * (x - a)

# たわみ曲線 EI * y''(x) = M(x)
# 左区間 0 <= x < a
C1, C2 = sp.symbols('C1 C2')
theta1 = sp.integrate(Mx_left / EI, x) + C1
y1 = sp.integrate(theta1, x) + C2

# 右区間 a <= x <= L
C3, C4 = sp.symbols('C3 C4')
theta2 = sp.integrate(Mx_right / EI, x) + C3
y2 = sp.integrate(theta2, x) + C4

# 境界・接続条件
eqs = [
    y1.subs(x, 0),               # y(0) = 0
    theta1.subs(x, 0),           # y'(0) = 0
    y2.subs(x, L),               # y(L) = 0
    theta2.subs(x, L),           # y'(L) = 0
    y1.subs(x, a) - y2.subs(x, a),     # たわみの連続
    theta1.subs(x, a) - theta2.subs(x, a)  # 回転角の連続
]

sol = sp.solve(eqs, [C1, C2, C3, C4])

# 定数を代入
y1_full = y1.subs(sol)
y2_full = y2.subs(sol)

# 数値設定
L_val = 10
a_val = 4
b_val = L_val - a_val
P_val = 100
EI_val = 1

subs_dict = {L: L_val, a: a_val, b: b_val, P: P_val, EI: EI_val}
y1_func = sp.lambdify(x, y1_full.subs(subs_dict), "numpy")
y2_func = sp.lambdify(x, y2_full.subs(subs_dict), "numpy")

# 数値描画
x_vals1 = np.linspace(0, a_val, 200)
x_vals2 = np.linspace(a_val, L_val, 200)
y_vals1 = y1_func(x_vals1)
y_vals2 = y2_func(x_vals2)

plt.figure(figsize=(10, 4))
plt.plot(x_vals1, y_vals1, label="左区間 (0 <= x < a)")
plt.plot(x_vals2, y_vals2, label="右区間 (a <= x <= L)")
plt.axhline(0, color='gray', linestyle='--')
plt.title("たわみ曲線（両端固定梁・EI=1）")
plt.xlabel("位置 x [m]")
plt.ylabel("たわみ y(x) [m]")
plt.legend()
plt.grid(True)
plt.show()
```
# Gemini先生へ

# copilot先生へ

# いつもの? sympyの実行環境と 参考のおすすめです。
[(テンプレート)](https://qiita.com/mrrclb48z/items/00dd08b0317069be9342)

https://qiita.com/mrrclb48z/items/b6351b48e47bcf6265c0

# いつもと違うおすすめです。
#### Qiita内