added all files reserch
This commit is contained in:
118
11g.py
Normal file
118
11g.py
Normal file
@@ -0,0 +1,118 @@
|
||||
import numpy as np
|
||||
import matplotlib.pyplot as plt
|
||||
|
||||
# --- 1. Определение параметров моделирования ---
|
||||
|
||||
# Геометрические параметры (1D модель: только глубина Z)
|
||||
DZ = 0.1 # Размер ячейки по глубине (Z) в метрах (10 см)
|
||||
Z_MAX = 2.0 # Максимальная глубина моделирования в метрах
|
||||
L_MAX = 10.0 # Максимальная длина (не используется в 1D модели)
|
||||
W_MAX = 22.0 # Максимальная ширина (не используется в 1D модели)
|
||||
|
||||
# Количество узлов (ячеек) по глубине
|
||||
N_NODES = int(Z_MAX / DZ) + 1
|
||||
DEPTHS = np.linspace(0, Z_MAX, N_NODES)
|
||||
|
||||
# Теплофизические параметры грунта (приближенные значения для талого грунта)
|
||||
LAMBDA = 1.5 # Теплопроводность грунта (λ), Вт/(м·К)
|
||||
RHO_C = 2.0e6 # Объемная теплоемкость (ρ·C), Дж/(м³·К)
|
||||
ALPHA = LAMBDA / RHO_C # Температуропроводность (α), м²/с
|
||||
|
||||
# Параметры времени
|
||||
DT_HOUR = 3600 # Шаг по времени (Δt) в секундах (1 час)
|
||||
N_DAYS = 365 # Продолжительность моделирования в днях (1 год)
|
||||
N_STEPS = N_DAYS * 24 # Общее количество временных шагов
|
||||
|
||||
# Критерий устойчивости (Число Фурье, r)
|
||||
R = (ALPHA * DT_HOUR) / (DZ**2)
|
||||
|
||||
# Проверка устойчивости явной схемы
|
||||
if R > 0.5:
|
||||
print(f"ВНИМАНИЕ: Нарушен критерий устойчивости (R = {R:.4f}).")
|
||||
print("Уменьшите шаг по времени (DT_HOUR) или шаг по пространству (DZ).")
|
||||
R = 0.5 # Принудительное ограничение для демонстрации
|
||||
else:
|
||||
print(f"Критерий устойчивости соблюден (R = {R:.4f} <= 0.5).")
|
||||
|
||||
# --- 2. Инициализация температуры ---
|
||||
|
||||
# Начальная температура грунта (равномерное распределение)
|
||||
T_INITIAL = 5.0 # °C
|
||||
Temperature = np.full(N_NODES, T_INITIAL)
|
||||
|
||||
# Массив для записи результатов (для построения графика)
|
||||
temp_history = [Temperature.copy()]
|
||||
|
||||
# --- 3. Определение граничных условий (ГКУ) ---
|
||||
|
||||
def surface_temperature(step):
|
||||
"""
|
||||
Граничное условие (ГКУ) на поверхности (z=0).
|
||||
Используется синусоидальная функция для имитации сезонного цикла (1 год).
|
||||
"""
|
||||
time_in_hours = step * DT_HOUR
|
||||
time_in_years = time_in_hours / (365 * 24 * 3600)
|
||||
|
||||
# Параметры: T_avg = 0°C, Amplitude = 20°C, сдвиг фазы (начало зимы)
|
||||
T_avg = 0.0
|
||||
T_amp = 20.0
|
||||
# Фаза: +pi/2, чтобы начать симуляцию с T(0) = T_avg
|
||||
return T_avg + T_amp * np.sin(2 * np.pi * time_in_years + np.pi/2)
|
||||
|
||||
# ГКУ на нижней границе (z=Z_MAX) - постоянная температура
|
||||
T_BOTTOM = T_INITIAL
|
||||
|
||||
# --- 4. Цикл моделирования ---
|
||||
|
||||
print(f"Начало моделирования: {N_DAYS} дней ({N_STEPS} шагов по 1 часу)...")
|
||||
|
||||
for n in range(N_STEPS):
|
||||
T_old = Temperature.copy()
|
||||
|
||||
# 1. Применение граничных условий
|
||||
# Верхняя граница (i=0) - Температура воздуха (Dirichlet BC)
|
||||
T_surface = surface_temperature(n)
|
||||
Temperature[0] = T_surface
|
||||
|
||||
# Нижняя граница (i=N_NODES-1) - Постоянная температура (Dirichlet BC)
|
||||
Temperature[-1] = T_BOTTOM
|
||||
|
||||
# 2. Расчет температуры для внутренних узлов (i=1 до N_NODES-2)
|
||||
# Формула явной схемы FDM: T_i^{n+1} = T_i^n (1 - 2r) + r (T_{i-1}^n + T_{i+1}^n)
|
||||
for i in range(1, N_NODES - 1):
|
||||
# --- Здесь должно быть место для учета фазовых переходов (мерзлота/талый грунт) ---
|
||||
# В реальной модели R и T_i^{n+1} должны рассчитываться с учетом
|
||||
# изменения LAMBDA, RHO_C и скрытой теплоты L (L_v, формула 3.13)
|
||||
# в зависимости от T_i^n и температуры фазового перехода (T_bf, формула 3.7).
|
||||
# В этой упрощенной модели LAMBDA, RHO_C, R - константы.
|
||||
# ---------------------------------------------------------------------------------
|
||||
|
||||
T_new = T_old[i] * (1 - 2 * R) + R * (T_old[i-1] + T_old[i+1])
|
||||
Temperature[i] = T_new
|
||||
|
||||
# Запись истории температуры каждые 90 дней для графика
|
||||
if (n % (90 * 24) == 0) and (n > 0):
|
||||
temp_history.append(Temperature.copy())
|
||||
|
||||
temp_history.append(Temperature.copy())
|
||||
print("Моделирование завершено.")
|
||||
|
||||
# --- 5. Визуализация результатов ---
|
||||
|
||||
plt.figure(figsize=(10, 6))
|
||||
time_labels = [f"День {int(i / 24)}" for i in np.linspace(0, N_STEPS, len(temp_history))]
|
||||
|
||||
# Добавление начального состояния
|
||||
plt.plot(temp_history[0], -DEPTHS, label=f't=0 (Начальное)', linestyle='--')
|
||||
|
||||
# Построение графиков для разных моментов времени
|
||||
for i, T_profile in enumerate(temp_history[1:]):
|
||||
plt.plot(T_profile, -DEPTHS, label=f'{time_labels[i+1]}', linewidth=2)
|
||||
|
||||
plt.xlabel('Температура, °C')
|
||||
plt.ylabel('Глубина, м')
|
||||
plt.title('Одномерное моделирование теплопереноса в грунте (1 год)')
|
||||
plt.grid(True, linestyle=':', alpha=0.6)
|
||||
plt.legend(title='Время')
|
||||
plt.axvline(x=0, color='grey', linestyle='-')
|
||||
plt.show()
|
||||
Reference in New Issue
Block a user