Форум программистов, компьютерный форум, киберфорум
MS Office Excel
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
0 / 0 / 0
Регистрация: 06.05.2025
Сообщений: 1

График дежурств

06.05.2025, 09:36. Показов 1302. Ответов 4
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
При составлении графика дежурств на год по месяцам раскидать отпуска в автоматическом режиме на каждого персонально с определённого дня
Может у кого есть варианты
0
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
06.05.2025, 09:36
Ответы с готовыми решениями:

Список дежурств
Друзья, помогите пожалуйста! У меня есть свод всех сотрудников. Ежедневно, мне высылают список...

Создать график
Создать график ...

График периодических работ
Как в Exel можно составлять графики плановых периодических ремонтов? Например имеются следующие...

4
Одесса - Украина
 Аватар для MikeVol
517 / 196 / 69
Регистрация: 01.04.2020
Сообщений: 610
07.05.2025, 07:42
SergLarine, В сети полно вариантов, стоило только вам задать запрос...
0
 Аватар для volodin661
6625 / 2256 / 346
Регистрация: 10.12.2013
Сообщений: 7,803
07.05.2025, 14:59
Цитата Сообщение от SergLarine Посмотреть сообщение
Может у кого есть варианты
Безусловно.

Только зачем здесь Excel ?
0
 Аватар для volodin661
6625 / 2256 / 346
Регистрация: 10.12.2013
Сообщений: 7,803
07.05.2025, 15:25
Спрашивать надо не здесь.
Потому как ныне есть в ынтрнете пацаны искуственные, но интеллектуальные.
Истратил 4 минуты.


Code
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
C# language: создание графика ежедневных дежурств на 1 год по месяцам с учетом отпусков.
Ввод данных из конфигурационного файла  YAML. с ключами: {name; email; phone}. 
Вывод по месяцам и по сотруднику. 
Вывод в формате XLSX. 
Использовать библиотеку NPOI.
 Показать пример возможного вывода. 
 Предусмотреть вывод дней дежурства в Google Calendar по каждому сотруднику, используя его почтовый адрес. 
 Использовать для примера следующие имена сотрудников, email-адреса и номера телефонов:
 
Сэм Кук; sam.cook@gmail.com; +79033512345
Вячеслав Малежик; slava.malezhik@gmail.com; +79168752376
Владимир Шахрин; vladimir.shakhrin@gmail.com; +79259663456
Гарик Сукачёв; gary.sukachev@gmail.com;+79159871255
Кори Тейлор; cory.taylor@gmail.com; +79293474578
Виктор Зинчук; victor.zinchuk@gmail.com; +79258900098
Юрий Антонов; jury.antonov@gmail.com; +79017634278

Конечно, давайте разработаем решение для создания графика ежедневных дежурств в C#, используя YAML для конфигурации, NPOI для вывода в XLSX и предоставляя возможность интеграции с Google Calendar.

Обзор решения:

Code
1
2
3
4
5
Чтение конфигурации: Загружаем данные сотрудников (имя, email, телефон) из YAML-файла.
Генерация графика: Создаем график дежурств на год, учитывая потенциальные периоды отпусков (которые могут быть добавлены в YAML или другим способом).
Вывод в XLSX: Используем библиотеку NPOI для сохранения графика в формате XLSX.
Вывод по сотруднику: Генерируем отдельный лист в XLSX или отдельный файл для каждого сотрудника с его дежурствами.
Интеграция с Google Calendar: Для каждого сотрудника создаем события в Google Calendar на основе его дежурств.
Шаг 1: Структура YAML-файла

Создадим файл config.yaml со следующей структурой:
JSON
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
employees:
  - name: Сэм Кук
    email: sam.cook@gmail.com
    phone: +79033512345
    vacation:
      - start: 2024-07-15
        end: 2024-07-30
  - name: Вячеслав Малежик
    email: slava.malezhik@gmail.com
    phone: +79168752376
    vacation: []
  - name: Владимир Шахрин
    email: vladimir.shakhrin@gmail.com
    phone: +79259663456
    vacation:
      - start: 2024-08-01
        end: 2024-08-15
  - name: Гарик Сукачёв
    email: gary.sukachev@gmail.com
    phone: +79159871255
    vacation: []
  - name: Кори Тейлор
    email: cory.taylor@gmail.com
    phone: +79293474578
    vacation: []
  - name: Виктор Зинчук
    email: victor.zinchuk@gmail.com
    phone: +79258900098
    vacation: []
  - name: Юрий Антонов
    email: jury.antonov@gmail.com
    phone: +79017634278
    vacation: []
Шаг 2: Модели данных в C#

Создадим классы для представления данных из YAML:

C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
public class Employee
{
    public string Name { get; set; }
    public string Email { get; set; }
    public string Phone { get; set; }
    public List<VacationPeriod> Vacation { get; set; } = new List<VacationPeriod>();
}
 
public class VacationPeriod
{
    public DateTime Start { get; set; }
    public DateTime End { get; set; }
}
 
public class Config
{
    public List<Employee> Employees { get; set; }
}

Шаг 3: Чтение YAML-файла


Для чтения YAML-файла используем библиотеку YamlDotNet. Установите ее через NuGet:
PowerShell
1
Install-Package YamlDotNet.
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
using YamlDotNet.Serialization;
using YamlDotNet.Serialization.NamingConventions;
 
public static class ConfigReader
{
    public static Config Read(string filePath)
    {
        var input = new StringReader(File.ReadAllText(filePath));
        var deserializer = new DeserializerBuilder()
            .WithNamingConvention(CamelCaseNamingConvention.Instance)
            .Build();
        return deserializer.Deserialize<Config>(input);
    }
}
Шаг 4: Генерация графика дежурств

Алгоритм генерации графика может быть разным в зависимости от ваших требований (например, равномерное распределение, учет выходных и праздников). Для простоты, давайте сделаем простую циклическую генерацию, пропуская дни отпуска.

C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
public class ScheduleGenerator
{
    public Dictionary<DateTime, Employee> Generate(List<Employee> employees, DateTime startDate, int days)
    {
        var schedule = new Dictionary<DateTime, Employee>();
        var currentDate = startDate;
        var employeeIndex = 0;
 
        for (int i = 0; i < days; i++)
        {
            var currentEmployee = employees[employeeIndex % employees.Count];
 
            // Проверяем, находится ли сотрудник в отпуске
            bool isVacation = currentEmployee.Vacation.Any(v => currentDate >= v.Start && currentDate <= v.End);
 
            if (!isVacation)
            {
                schedule[currentDate] = currentEmployee;
                employeeIndex++; // Переходим к следующему сотруднику только если он не в отпуске
            }
            else
            {
                // Если сотрудник в отпуске, этот день дежурит следующий доступный сотрудник
                int nextEmployeeIndex = employeeIndex + 1;
                while (true)
                {
                    var nextEmployee = employees[nextEmployeeIndex % employees.Count];
                    bool isNextEmployeeVacation = nextEmployee.Vacation.Any(v => currentDate >= v.Start && currentDate <= v.End);
                    if (!isNextEmployeeVacation)
                    {
                        schedule[currentDate] = nextEmployee;
                        employeeIndex++; // Переходим к следующему сотруднику после того, кто дежурил
                        break;
                    }
                    nextEmployeeIndex++;
                }
            }
            currentDate = currentDate.AddDays(1);
        }
 
        return schedule;
    }
}
Шаг 5: Вывод в XLSX с NPOI

Установите библиотеку NPOI через NuGet:
PowerShell
1
 Install-Package NPOI.
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
using NPOI.SS.UserModel;
using NPOI.XSSF.UserModel;
 
public class ExcelExporter
{
    public void Export(Dictionary<DateTime, Employee> schedule, string filePath)
    {
        IWorkbook workbook = new XSSFWorkbook();
 
        // Вывод по месяцам
        CreateMonthlySheet(workbook, schedule);
 
        // Вывод по сотруднику
        CreateEmployeeSheets(workbook, schedule);
 
        using (var fileStream = new FileStream(filePath, FileMode.Create, FileAccess.Write))
        {
            workbook.Write(fileStream);
        }
    }
 
    private void CreateMonthlySheet(IWorkbook workbook, Dictionary<DateTime, Employee> schedule)
    {
        ISheet sheet = workbook.CreateSheet("График по месяцам");
 
        // Заголовки
        IRow headerRow = sheet.CreateRow(0);
        headerRow.CreateCell(0).SetCellValue("Дата");
        headerRow.CreateCell(1).SetCellValue("Дежурный");
 
        int rowIndex = 1;
        foreach (var entry in schedule.OrderBy(e => e.Key))
        {
            IRow row = sheet.CreateRow(rowIndex++);
            row.CreateCell(0).SetCellValue(entry.Key.ToShortDateString());
            row.CreateCell(1).SetCellValue(entry.Value.Name);
        }
 
        // Группировка по месяцам (опционально, для удобства просмотра)
        // Можно добавить пустые строки или заголовки для каждого месяца
    }
 
    private void CreateEmployeeSheets(IWorkbook workbook, Dictionary<DateTime, Employee> schedule)
    {
        var employeeSchedule = schedule.GroupBy(e => e.Value)
                                       .ToDictionary(g => g.Key, g => g.Select(e => e.Key).ToList());
 
        foreach (var entry in employeeSchedule)
        {
            var employee = entry.Key;
            var dutyDates = entry.Value.OrderBy(d => d).ToList();
 
            ISheet sheet = workbook.CreateSheet(employee.Name);
 
            // Заголовки
            IRow headerRow = sheet.CreateRow(0);
            headerRow.CreateCell(0).SetCellValue("Дата дежурства");
 
            int rowIndex = 1;
            foreach (var date in dutyDates)
            {
                IRow row = sheet.CreateRow(rowIndex++);
                row.CreateCell(0).SetCellValue(date.ToShortDateString());
            }
        }
    }
}
Шаг 6: Интеграция с Google Calendar

Для работы с Google Calendar API вам потребуется настроить проект в Google Cloud Platform, включить Calendar API и получить учетные данные (например, JSON-файл). Установите клиентскую библиотеку Google Calendar API для .NET: Install-Package Google.Apis.Calendar.v3.

Вот пример базовой реализации:
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
using Google.Apis.Auth.OAuth2;
using Google.Apis.Calendar.v3;
using Google.Apis.Calendar.v3.Data;
using Google.Apis.Services;
using Google.Apis.Util.Store;
 
public class GoogleCalendarExporter
{
    private readonly string[] Scopes = { CalendarService.Scope.CalendarEvents };
    private readonly string ApplicationName = "Duty Schedule App";
 
    public async Task Export(Dictionary<DateTime, Employee> schedule, string credentialsPath)
    {
        UserCredential credential;
        using (var stream = new FileStream(credentialsPath, FileMode.Open, FileAccess.Read))
        {
            string credPath = "token.json";
            credential = await GoogleWebAuthorizationBroker.AuthorizeAsync(
                GoogleClientSecrets.FromStream(stream).Secrets,
                Scopes,
                "user",
                CancellationToken.None,
                new FileDataStore(credPath, true));
        }
 
        var service = new CalendarService(new BaseClientService.Initializer()
        {
            HttpClientInitializer = credential,
            ApplicationName = ApplicationName,
        });
 
        // Группировка по сотруднику
        var employeeSchedule = schedule.GroupBy(e => e.Value)
                                       .ToDictionary(g => g.Key, g => g.Select(e => e.Key).ToList());
 
        foreach (var entry in employeeSchedule)
        {
            var employee = entry.Key;
            var dutyDates = entry.Value.OrderBy(d => d).ToList();
 
            foreach (var date in dutyDates)
            {
                var eventBody = new Event
                {
                    Summary = "Дежурство",
                    Description = $"Ежедневное дежурство. Контакты: {employee.Phone}",
                    Start = new EventDateTime
                    {
                        Date = date.ToString("yyyy-MM-dd"),
                        TimeZone = "Europe/Moscow", // Укажите ваш часовой пояс
                    },
                    End = new EventDateTime
                    {
                        Date = date.ToString("yyyy-MM-dd"),
                        TimeZone = "Europe/Moscow", // Укажите ваш часовой пояс
                    },
                    Attendees = new List<EventAttendee>
                    {
                        new EventAttendee { Email = employee.Email }
                    },
                    Reminders = new Event.RemindersData
                    {
                        UseDefault = false,
                        Overrides = new List<EventReminder>
                        {
                            new EventReminder { Method = "email", Minutes = 24 * 60 }, // Напоминание за 24 часа
                            new EventReminder { Method = "popup", Minutes = 60 }     // Напоминание за 1 час
                        }
                    }
                };
 
                try
                {
                    // Создание события в календаре сотрудника
                    // Важно: У сотрудника должен быть доступ на запись в его календарь для вашего сервиса
                    // или вы можете создать событие в своем календаре и пригласить сотрудника.
                    // Для простоты, предположим, что сервис имеет доступ к календарям сотрудников.
                    // В реальной ситуации, вам, возможно, потребуется использовать Service Account
                    // и делегировать доступ к календарям пользователей.
                    var request = service.Events.Insert("primary", eventBody); // 'primary' - это календарь текущего пользователя
                    var createdEvent = await request.ExecuteAsync();
                    Console.WriteLine($"Событие дежурства для {employee.Name} на {date.ToShortDateString()} создано: {createdEvent.HtmlLink}");
                }
                catch (Exception ex)
                {
                    Console.WriteLine($"Ошибка при создании события для {employee.Name} на {date.ToShortDateString()}: {ex.Message}");
                    // Обработка ошибок, например, если у сервиса нет доступа к календарю
                }
            }
        }
    }
}
0
 Аватар для volodin661
6625 / 2256 / 346
Регистрация: 10.12.2013
Сообщений: 7,803
07.05.2025, 15:29
Ну и так далее, как говорил Велемир Хлебников, обрывая чтение своих стихов на середине.

В Google Calendar я не играл, а всё остальное собралось
Миниатюры
График дежурств  
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
07.05.2025, 15:29
Помогаю со студенческими работами здесь

построить график функций
помогите построить график функции: y=3sin^2(nx), где x (квадратные скобки) -1;1 с шагом 0.2

график
ГОРЮ. Помогите построить графики функций... 1. Х принадлеж. ......3+sin(x)/1=x^2 при ...

График функции в Excel
Собственно надо сделать график в excel, тока я не знаю как делать может кто нить научить или...

построить график функции
Оч надеюсь что кто-нибудь поможет(((

Как построить график функции sin?
как посторить график функции sin(x) в excel? понятно что таблица значений нужно.но вот какие...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
5
Ответ Создать тему
Новые блоги и статьи
Access
VikBal 11.12.2025
Помогите пожалуйста !! Как объединить 2 одинаковые БД Access с разными данными.
Новый ноутбук
volvo 07.12.2025
Всем привет. По скидке в "черную пятницу" взял себе новый ноутбук Lenovo ThinkBook 16 G7 на Амазоне: Ryzen 5 7533HS 64 Gb DDR5 1Tb NVMe 16" Full HD Display Win11 Pro
Музыка, написанная Искусственным Интеллектом
volvo 04.12.2025
Всем привет. Некоторое время назад меня заинтересовало, что уже умеет ИИ в плане написания музыки для песен, и, собственно, исполнения этих самых песен. Стихов у нас много, уже вышли 4 книги, еще 3. . .
От async/await к виртуальным потокам в Python
IndentationError 23.11.2025
Армин Ронахер поставил под сомнение async/ await. Создатель Flask заявляет: цветные функции - провал, виртуальные потоки - решение. Не threading-динозавры, а новое поколение лёгких потоков. Откат?. . .
Поиск "дружественных имён" СОМ портов
Argus19 22.11.2025
Поиск "дружественных имён" СОМ портов На странице: https:/ / norseev. ru/ 2018/ 01/ 04/ comportlist_windows/ нашёл схожую тему. Там приведён код на С++, который показывает только имена СОМ портов, типа,. . .
Сколько Государство потратило денег на меня, обеспечивая инсулином.
Programma_Boinc 20.11.2025
Сколько Государство потратило денег на меня, обеспечивая инсулином. Вот решила сделать интересный приблизительный подсчет, сколько государство потратило на меня денег на покупку инсулинов. . . .
Ломающие изменения в C#.NStar Alpha
Etyuhibosecyu 20.11.2025
Уже можно не только тестировать, но и пользоваться C#. NStar - писать оконные приложения, содержащие надписи, кнопки, текстовые поля и даже изображения, например, моя игра "Три в ряд" написана на этом. . .
Мысли в слух
kumehtar 18.11.2025
Кстати, совсем недавно имел разговор на тему медитаций с людьми. И обнаружил, что они вообще не понимают что такое медитация и зачем она нужна. Самые базовые вещи. Для них это - когда просто люди. . .
Создание Single Page Application на фреймах
krapotkin 16.11.2025
Статья исключительно для начинающих. Подходы оригинальностью не блещут. В век Веб все очень привыкли к дизайну Single-Page-Application . Быстренько разберем подход "на фреймах". Мы делаем одну. . .
Фото: Daniel Greenwood
kumehtar 13.11.2025
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru