# Техническое задание: источники данных ## Задача Реализовать три независимых источника данных для формирования `MyList`: - `ManualDataSource`; - `RandomDataSource`; - `FileDataSource`. Все источники должны формировать только валидные объекты `Student`. Класс `Student` содержит: ```java private final String groupNumber; private final double averageGrade; private final String recordBookNumber; ``` Создание объектов `Student` выполнять через `StudentBuilder`. --- # Общий контракт Создать интерфейс `DataSource`: ```java public interface DataSource { MyList create(); } ``` Источник данных не должен самостоятельно получать данные от пользователя. Все необходимые входные значения должны передаваться извне. Результатом работы каждого источника является `MyList`. Стандартные `List`, `ArrayList` и `LinkedList` для хранения результата не использовать. --- # `ManualDataSource` ## Назначение Постепенно формировать коллекцию `Student` на основе значений, передаваемых извне для каждого отдельного объекта. ## Входные данные одного объекта Для создания одного `Student` передаются: ```text groupNumber averageGrade recordBookNumber ``` Также передаётся `index` — позиция в коллекции, на которой должен находиться создаваемый объект. Размер результирующей коллекции задаётся заранее. ## Контракт `ManualDataSource` должен: 1. Принимать требуемый размер коллекции. 2. Принимать значения одного `Student`: - `groupNumber`; - `averageGrade`; - `recordBookNumber`. 3. Принимать индекс, на котором должен находиться этот объект. 4. Создавать новый `Student` через `StudentBuilder`. 5. Добавлять созданный объект в нужную позицию коллекции. 6. Позволять повторно передавать данные для существующего индекса, заменяя объект на новый. 7. Проверять допустимость индекса. 8. Не изменять уже созданный объект `Student`. 9. Позволять получить текущее состояние коллекции для просмотра. 10. После заполнения вернуть сформированную `MyList`. Рекомендуемый метод для передачи одного объекта: ```java setStudent( int index, String groupNumber, double averageGrade, String recordBookNumber ) ``` Таким образом, пользовательский код может последовательно передать данные для всех элементов: ```java dataSource.setStudent(0, "101", 4.5, "10001"); dataSource.setStudent(1, "102", 3.8, "10002"); dataSource.setStudent(2, "101", 4.9, "10003"); ``` После заполнения: ```java MyList students = dataSource.create(); ``` ### Изменение объекта Для изменения объекта повторно вызывается `setStudent(...)` с нужным индексом: ```java dataSource.setStudent(1, "105", 4.2, "10025"); ``` Объект на позиции `1` заменяется новым валидным `Student`. ### Размер коллекции Если задан: ```text size = 5 ``` то для успешного создания коллекции должны быть заданы данные для всех пяти позиций: ```text 0 1 2 3 4 ``` Порядок заполнения не обязан совпадать с порядком индексов: ```java dataSource.setStudent(3, "103", 4.1, "10004"); dataSource.setStudent(0, "101", 4.5, "10001"); dataSource.setStudent(4, "102", 3.9, "10005"); dataSource.setStudent(1, "101", 4.8, "10002"); dataSource.setStudent(2, "104", 3.7, "10003"); ``` После заполнения коллекция должна содержать ровно пять объектов в соответствии с указанными индексами. Если хотя бы одна позиция не заполнена, `create()` должен сообщить об ошибке и не возвращать неполную коллекцию. --- # `RandomDataSource` ## Назначение Создавать заданное количество `Student` со случайными значениями в диапазонах, заданных извне. ## Входные данные Передаются: ```text size ``` и диапазоны для каждого поля: ```text groupNumber: minimum maximum averageGrade: minimum maximum recordBookNumber: minimum maximum ``` ## Контракт `RandomDataSource` должен: 1. Принять размер создаваемой коллекции. 2. Принять минимальное и максимальное значение каждого поля. 3. Проверить корректность каждого диапазона. 4. Сгенерировать значения в заданных пределах. 5. Создать каждый объект через `StudentBuilder`. 6. Поместить объекты в `MyList`. 7. Вернуть коллекцию заданного размера. Минимальное и максимальное значения включаются в диапазон генерации. `RandomDataSource` не должен самостоятельно получать или отображать параметры генерации. --- # `FileDataSource` ## Назначение Создавать `MyList` на основании содержимого файла. ## Входные данные Передаётся **абсолютный путь к файлу**. Относительный путь не является входным параметром `FileDataSource`. Формат одной записи: ```text groupNumber;averageGrade;recordBookNumber ``` Пример: ```text 101;4.75;123456 102;3.80;123457 103;4.20;123458 ``` ## Контракт `FileDataSource` должен: 1. Получить абсолютный путь к файлу. 2. Открыть файл. 3. Последовательно обработать его записи. 4. Разделить каждую запись на три значения. 5. Создать `Student` через `StudentBuilder`. 6. Добавить только валидные объекты в `MyList`. 7. Пропустить некорректную запись и продолжить обработку остальных. 8. При невозможности открыть файл сообщить об ошибке. 9. Вернуть сформированную `MyList`. --- # Общие требования 1. Все источники должны создавать `Student` только через `StudentBuilder`. 2. Источник данных не должен самостоятельно вводить данные. 3. Источник данных не должен зависеть от интерфейса пользователя. 4. Источник данных не должен содержать логику сортировки. 5. Результат хранить только в `MyList`. 6. Невалидный `Student` не должен попасть в коллекцию. 7. Проверка корректности самого объекта выполняется средствами `Student`. 8. Для ручного заполнения изменение существующего `Student` выполнять заменой объекта, а не изменением его полей. --- # Примеры тестов ## `ManualDataSource` ### Заполнение всей коллекции Создать источник размера `3`: ```java ManualDataSource dataSource = new ManualDataSource(3); dataSource.setStudent(0, "101", 4.5, "10001"); dataSource.setStudent(1, "102", 3.8, "10002"); dataSource.setStudent(2, "103", 4.2, "10003"); MyList result = dataSource.create(); ``` Проверить: ```text result.size() == 3 ``` и соответствие каждого объекта своему индексу. ### Заполнение в произвольном порядке ```java dataSource.setStudent(2, "103", 4.2, "10003"); dataSource.setStudent(0, "101", 4.5, "10001"); dataSource.setStudent(1, "102", 3.8, "10002"); ``` Проверить правильное расположение объектов. ### Изменение объекта После заполнения: ```java dataSource.setStudent(1, "105", 4.9, "10025"); ``` Проверить, что изменился только объект с индексом `1`. ### Незаданный индекс Для коллекции размера `3` вызвать: ```java dataSource.setStudent(3, ...); ``` Проверить выброс исключения. ### Неполное заполнение Заполнить только две позиции из трёх и вызвать `create()`. Проверить, что неполная коллекция не возвращается. --- ## `RandomDataSource` ### Корректная генерация Задать размер `100` и допустимые диапазоны для всех трёх полей. Проверить: ```text result.size() == 100 ``` и нахождение каждого значения внутри заданного диапазона. ### Граничный диапазон Задать одинаковые минимальное и максимальное значения. Проверить, что все сгенерированные значения соответствуют этому значению. ### Некорректный диапазон Задать: ```text minimum > maximum ``` Проверить выброс исключения. --- ## `FileDataSource` ### Корректный файл Для файла: ```text 101;4.75;123456 102;3.80;123457 103;4.20;123458 ``` проверить получение трёх корректных объектов. ### Файл с некорректной записью ```text 101;4.75;123456 invalid;abc;123457 103;4.20;123458 ``` Проверить, что в коллекцию попадают только две корректные записи. ### Пустой файл Проверить получение пустой коллекции. ### Несуществующий файл Передать путь к несуществующему файлу и проверить корректную обработку ошибки. --- # Результат Реализовать: ```text DataSource.java ManualDataSource.java RandomDataSource.java FileDataSource.java ``` Допускается создание вспомогательных классов для чтения файла и генерации случайных значений.