Рабочее пространство на основе DrWatson
Рабочее пространство на основе DrWatson.
Содержание
1 Подходы организации рабочего пространства
- Подходы:
- один проект на все работы;
- отдельный проект на каждую работу.
| Критерий | Один проект на все работы | Отдельный проект на каждую работу |
|---|---|---|
| Изоляция зависимостей | Риск конфликтов версий пакетов между работами | Полная изоляция, каждая работа автономна |
| Управление пакетами | Сложно, если работы требуют разных версий пакетов | Просто, каждая работа имеет свой Project.toml |
| Структура проекта | Может стать громоздкой (много папок data_*, scripts_*) | Чисто, стандартная структура DrWatson |
| Общие утилиты | Легко делиться общим кодом через src/ | Приходится копировать или выносить в отдельный пакет |
| Запуск всех работ | Просто запустить последовательно | Нужно переключать активацию проектов |
| Версионность (Git) | Один репозиторий для всего | Отдельные репозитории или подмодули |
| Сдача на проверку | Сложно выделить одну работу | Просто отправить папку проекта |
| Долгосрочная поддержка | Риск распухания проекта | Легко архивировать, удалять, обновлять отдельные работы |
Выберите отдельные проекты, если:
- Лабораторные работы тематически разные
- Требуются разные версии пакетов
- Работы будут сдаваться по отдельности
- Планируете использовать работы в будущих курсах
Выберите единый проект, если:
- Все работы используют одинаковые пакеты
- Лабораторные последовательно развивают одну тему
- Много общего кода между работами
- Упрощенное управление — приоритет
1.1 Оптимальная стратегия
- Начинайте с отдельных проектов — это безопаснее
- Стандартизируйте структуру (одинаковые имена скриптов в каждой работе)
- Создайте метапроект для удобного запуска всех работ
- Выносите общий код в отдельный пакет (если появится много общего):
# В каждом проекте using Pkg Pkg.add(url="https://github.com/yourname/CourseUtils.jl") using CourseUtils # Общие функции для всех работ
2 Гибридный подход “Метапроект + Изолированные подпроекты”
2.1 Структура
LabCourse_2024/ # Метапроект (обычная папка, не DrWatson)
├── README.md # Описание всего курса
├── run_all_labs.jl # Скрипт для запуска всех работ
├── common/ # Общие утилиты (если нужны)
│ ├── plotting_utils.jl
│ └── data_helpers.jl
├── lab1_exponential_growth/ # Проект DrWatson для лабы 1
│ ├── Project.toml
│ ├── scripts/
│ ├── data/
│ └── ...
├── lab2_logistic_growth/ # Проект DrWatson для лабы 2
│ ├── Project.toml
│ ├── scripts/
│ └── ...
├── lab3_sir_model/ # Проект DrWatson для лабы 3
│ └── ...
└── submissions/ # Готовые отчеты для сдачи
├── lab1_report.pdf
├── lab2_report.qmd
└── ...
2.2 Реализация гибридного подхода
2.2.1 Создание метапроекта и первой лабораторной работы
# В директории курса создаем первую лабораторную
cd("LabCourse_2024")
using DrWatson
initialize_project("lab1_exponential_growth"; authors="Ваше Имя")
# Аналогично для последующих работ
initialize_project("lab2_logistic_growth"; authors="Ваше Имя")
initialize_project("lab3_sir_model"; authors="Ваше Имя")
2.2.2 Скрипт для управления всеми работами run_all_labs.jl
# run_all_labs.jl - Запуск всех лабораторных работ последовательно
labs = [
"lab1_exponential_growth",
"lab2_logistic_growth",
"lab3_sir_model"
]
println("Запуск всех лабораторных работ курса")
println("="^50)
for lab in labs
println("\n▶ Запуск лабораторной работы: $lab")
println("-"^40)
# Переходим в директорию проекта
cd(lab) do
# Активируем окружение проекта
using Pkg
Pkg.activate(".")
# Запускаем основной скрипт лабораторной
try
include("scripts/main.jl")
println("✅ $lab завершена успешно")
catch e
println("❌ Ошибка в $lab: $e")
end
end
end
println("\n" * "="^50)
println("Все работы завершены!")
2.2.3 Стандартизация структуры каждой лабораторной
В каждой лабораторной создайте единую структуру.
Файл
scripts/main.jl(точка входа для каждой работы):# scripts/main.jl - Главный скрипт лабораторной работы using DrWatson @quickactivate "lab1_exponential_growth" # имя проекта println("="^50) println("ЛАБОРАТОРНАЯ РАБОТА 1: Экспоненциальный рост") println("="^50) # 1. Загрузка параметров include("scripts/01_parameters.jl") # 2. Запуск экспериментов include("scripts/02_run_experiments.jl") # 3. Анализ результатов include("scripts/03_analysis.jl") # 4. Генерация отчета include("scripts/04_generate_report.jl") println("Лабораторная работа завершена!")Файл
scripts/01_parameters.jl(единый формат для всех работ):# scripts/01_parameters.jl - Параметры лабораторной работы # Базовый эксперимент base_params = Dict( :experiment_name => "exponential_growth", :u0 => [1.0], :α => 0.3, :tspan => (0.0, 10.0), :solver => Tsit5(), :saveat => 0.1, :description => "Базовый экспоненциальный рост" ) # Сетка для параметрического исследования param_grid = Dict( :u0 => [[1.0]], :α => [0.1, 0.3, 0.5, 0.8, 1.0], :tspan => [(0.0, 10.0)], :solver => [Tsit5()], :saveat => [0.1], :experiment_name => ["parametric_scan"] ) println("Параметры загружены:") println("Базовый эксперимент: ", keys(base_params)) println("Параметрическая сетка: ", keys(param_grid))
2.2.4 Шаблон для быстрого создания новых лабораторных
- Создайте
template_make_new_lab.jl:# template_make_new_lab.jl - Создание шаблона новой лабораторной function create_new_lab(lab_name, lab_number, description) # Создаем проект DrWatson initialize_project(lab_name; authors="Ваше Имя") # Стандартная структура папок mkdir(scriptsdir("utils")) mkdir(datadir("raw")) mkdir(datadir("processed")) mkdir(plotsdir("figures")) mkdir(projectdir("reports")) # Создаем стандартные файлы files_to_create = [ ("scripts/main.jl", main_template(lab_name)), ("scripts/01_parameters.jl", params_template()), ("scripts/02_run_experiments.jl", experiments_template()), ("scripts/03_analysis.jl", analysis_template()), ("scripts/04_generate_report.jl", report_template()), ("README.md", readme_template(lab_name, lab_number, description)) ] for (path, content) in files_to_create open(projectdir(path), "w") do f write(f, content) end end println("Создана новая лабораторная: $lab_name") end # (Здесь должны быть функции-шаблоны для каждого файла) # Использование: create_new_lab("lab4_predator_prey", 4, "Модель Лотки-Вольтерры")
2.3 Пошаговое руководство для учебного курса
2.3.1 Для студентов (сдача отдельных работ)
Для каждой новой лабораторной:
# Создаем отдельный проект julia -e 'using DrWatson; initialize_project("lab2_logistic")' # Работаем внутри проекта cd lab2_logistic julia --project=. scripts/main.jl # Генерируем отчет для сдачи julia --project=. scripts/04_generate_report.jlСдача работы: просто заархивируйте папку проекта и отправьте преподавателю.
2.3.2 Для преподавателей (управление всем курсом)
Создайте репозиторий курса:
Course_Computational_Modelling/ ├── labs/ # Подмодули Git для каждой лабораторной │ ├── lab1/ │ ├── lab2/ │ └── ... ├── assignments/ # Формулировки заданий ├── solutions/ # Решения (отдельные проекты) └── run_course.jl # Запуск всех демонстрацийИспользуйте Git подмодули для изоляции:
git submodule add https://github.com/yourcourse/lab1.git labs/lab1 git submodule add https://github.com/yourcourse/lab2.git labs/lab2
3 Основные функции и использование
3.1 Активация проекта и пути
- Каждый скрипт в проекте должен начинаться так:
using DrWatson @quickactivate "MyProject" # Активирует окружение проекта - После активации вы можете использовать функции для получения путей, которые будут работать независимо от местоположения проекта:
projectdir()— путь к корню проекта.datadir("sims", "file.jld2")→".../MyProject/data/sims/file.jld2".srcdir(),plotsdir()— для папокsrcиplots.
3.2 Организация параметров и запуск симуляций
- Удобно хранить параметры в словарях.
- Макрос
@strdictсоздает словарь из существующих переменных, аdict_listгенерирует список словарей для перебора параметров:a, b = 1, 2 params = @strdict a b # Создает Dict("a"=>1, "b"=>2) # Генерация сетки параметров allparams = Dict("a" => [1, 2], "b" => [3, 4]) dicts = dict_list(allparams) # Вектор из 4 словарей
3.3 Автоматическое сохранение и загрузка результатов
Функция
produce_or_load— ключевой инструмент.Она проверяет, был ли уже рассчитан и сохранен результат для данного набора параметров.
Если файл существует, он загружается; если нет — запускается ваша функция расчета и результат сохраняется:
function run_simulation(params::Dict) @unpack a, b = params result = a + b # Ваши вычисления return merge(params, @strdict result) end for params in dicts data, filepath = produce_or_load( datadir("sims"), # Папка для сохранения params, # Параметры run_simulation, # Функция-расчет prefix="exp" # Префикс в имени файла ) endИмя файла автоматически формируется из параметров (например,
exp_a=1_b=3.jld2).
3.4 Сбор результатов в таблицу
- После запуска симуляций вы можете легко собрать все результаты из папки в одну таблицу (DataFrame):
using DataFrames df = collect_results(datadir("sims"))
4 Создание проекта
- Запустите
juliaи установите DrWatson:using Pkg Pkg.add("DrWatson") - Чтобы начать, установите и инициализируйте проект:
# Создайте структуру проекта в текущей директории using DrWatson initialize_project("project"; authors="Dmitry S. Kulyabov", git = false ) - Эта команда создаст папку
projectсо стандартной структурой: data/, plots/, scripts/, src/ и другие.
