You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
В данном проекте представлена реализация библиотеки string.h на языке программирования С с некоторыми дополнениями (с собственной реализацией функций sprintf и sscanf). Библиотека string.h является основной библиотекой языка С по обработке строк. В рамках этого проекта были отработаны навыки взаимодействия со строковыми данными и усилен структурный подход.
Библиотека String
Язык программирования C содержит набор функций, реализующих операции со строками (символьными строками и строками байтов) в своей стандартной библиотеке. В ней поддерживаются такие операции, как: копирование, конкатенация, маркировка и поиск. Для символьных строк в стандартной библиотеке существует правило, что строки должны заканчиваться терминирующим нуль-символом: строка из n символов представляется в виде массива из n + 1 элементов, последний из которых является символом «NULL».
Единственная поддержка строк, собственно, в языке программирования С заключается в том, что компилятор преобразует закавыченные строковые константы в строки, заканчивающиеся нулем.
Типы данных
№
Тип
Описание
1
size_t
Целочисленный тип без знака, являющийся результатом ключевого слова sizeof.
Вычисляет длину начального сегмента str1, который полностью состоит из символов, не входящих в str2.
10
char *strerror(int errnum)
Выполняет поиск во внутреннем массиве номера ошибки errnum и возвращает указатель на строку с сообщением об ошибке. Нужно объявить макросы, содержащие массивы сообщений об ошибке для операционных систем mac и linux. Описания ошибок есть в оригинальной библиотеке. Проверка текущей ОС осуществляется с помощью директив.
11
size_t strlen(const char *str)
Вычисляет длину строки str, не включая завершающий нулевой символ.
12
char *strpbrk(const char *str1, const char *str2)
Находит первый символ в строке str1, который соответствует любому символу, указанному в str2.
13
char *strrchr(const char *str, int c)
Выполняет поиск последнего вхождения символа c (беззнаковый тип) в строке, на которую указывает аргумент str.
Возвращает новую строку, в которой указанная строка (str) вставлена в указанную позицию (start_index) в данной строке (src). В случае какой-либо ошибки следует вернуть значение NULL.
Возвращает новую строку, в которой удаляются все начальные и конечные вхождения набора заданных символов (trim_chars) из данной строки (src). В случае какой-либо ошибки следует вернуть значение NULL.
sprintf() и sscanf()
// Считывает форматированный ввод из строкиintsscanf(constchar*str, constchar*format, ...)
// Отправляет форматированный вывод в строку, на которую указывает strintsprintf(char*str, constchar*format, ...)
str — это С-строка, которую функция обрабатывает в качестве источника для извлечения данных;
format — это С-строка, содержащая один или несколько следующих элементов: пробельный символ, непробельный символ и спецификаторы формата. Спецификатор формата для печатающих функций следует прототипу: %[флаги][ширина][.точность][длина]спецификатор. Спецификатор формата для сканирующих функций следует прототипу: %[*][ширина][длина]спецификатор.
Спецификаторы
№
Спецификатор
Результат sprintf
Результат sscanf
1
c
Символ
Символ
2
d
Знаковое десятичное целое число
Знаковое десятичное целое число
3
i
Знаковое десятичное целое число
Знаковое целое число (может быть десятичным, восьмеричным или шестнадцатеричным)
4
e
Научная нотация (мантисса/экспонента) с использованием символа e (вывод чисел должен совпадать с точностью до e-6)
Десятичное число с плавающей точкой или научная нотация (мантисса/экспонента)
5
E
Научная нотация (мантисса/экспонента) с использованием символа Е
Десятичное число с плавающей точкой или научная нотация (мантисса/экспонента)
6
f
Десятичное число с плавающей точкой
Десятичное число с плавающей точкой или научная нотация (мантисса/экспонента)
7
g
Использует кратчайший из представлений десятичного числа
Десятичное число с плавающей точкой или научная нотация (мантисса/экспонента)
8
G
Использует кратчайший из представлений десятичного числа
Десятичное число с плавающей точкой или научная нотация (мантисса/экспонента)
9
o
Беззнаковое восьмеричное число
Беззнаковое восьмеричное число
10
s
Строка символов
Строка символов
11
u
Беззнаковое десятичное целое число
Беззнаковое десятичное целое число
12
x
Беззнаковое шестнадцатеричное целое число
Беззнаковое шестнадцатеричное целое число (любые буквы)
13
X
Беззнаковое шестнадцатеричное целое число (заглавные буквы)
Беззнаковое шестнадцатеричное целое число (любые буквы)
14
p
Адрес указателя
Адрес указателя
15
n
Количество символов, напечатанных до появления %n
Количество символов, считаных до появления %n
16
%
Символ %
Символ %
Флаги sprintf()
№
Флаг
Описание
1
-
Выравнивание по левому краю в пределах заданной ширины поля. Выравнивание по правому краю используется по умолчанию (см. подспецификатор ширины).
2
+
Заставляет явно указывать знак плюс или минус (+ или -) даже для положительных чисел. По умолчанию только отрицательным числам предшествует знак «-».
3
(пробел)
Если знак не будет выведен, перед значением вставляется пробел.
4
#
При использовании со спецификаторами o, x или X перед числом вставляется 0, 0x или 0X соответственно (для значений, отличных от нуля). При использовании с e, E и f «заставляет» записанный вывод содержать десятичную точку, даже если за ней не последует никаких цифр. По умолчанию, если не следует никаких цифр, десятичная точка не записывается. При использовании с g или G результат такой же, как и с e или E, но конечные нули не удаляются.
5
0
Заполняет число слева нулями (0) вместо пробелов, где указан спецификатор ширины (см. подспецификатор ширины).
Ширина sprintf() и sscanf()
№
Ширина
Описание
1
(число)
Минимальное количество символов, печатаемых sprintf. Если выводимое значение короче этого числа, результат дополняется пробелами. Значение не усекается, даже если результат больше. Для sscanf это максимальное число символов, которые будут считываться для этого поля.
2
*
В sprintf знак * значит, что ширина указывается не в строке формата, а в качестве дополнительного аргумента целочисленного значения, предшествующего аргументу, который необходимо отформатировать. В sscanf знак *, помещенный после % и перед спецификатором формата, считывает данные указанного типа, но подавляет их присваивание.
Точность sprintf()
№
.точность
Описание
1
.число
Для целочисленных спецификаторов (d, i, o, u, x, X) — точность определяет минимальное количество записываемых цифр. Если записываемое значение короче этого числа, результат дополняется ведущими нулями. Значение не усекается, даже если результат длиннее. Точность 0 означает, что для значения 0 не записывается ни одного символа. Для спецификаторов e, E и f — это количество цифр, которые должны быть напечатаны после десятичной точки. Для спецификаторов g и G — это максимальное количество значащих цифр, которые должны быть напечатаны. Для s — это максимальное количество печатаемых символов. По умолчанию все символы печатаются до тех пор, пока не встретится терминирующий нуль. Для типа с — никак не влияет. Если точность не указана для спецификаторов e, E, f, g и G, то по умолчанию ее значение равно 6. Если точность не указана для остальных спецификаторов, то по умолчанию ее значение равно 1. Если число не указано (нет явного значения точности), то по умолчанию — 0.
2
.*
Точность указывается не в строке формата, а в качестве дополнительного аргумента целочисленного значения, предшествующего аргументу, который должен быть отформатирован.
Длина sprintf() и sscanf()
№
Длина
Описание
1
h
Аргумент интерпретируется как короткое int или короткое int без знака (применяется только к целочисленным спецификаторам: i, d, o, u, x и X).
2
l
Аргумент интерпретируется как длинное int или длинное int без знака для целочисленных спецификаторов (i, d, o, u, x и X) и как широкий символ или строка широких символов для спецификаторов c и s.
3
L
Аргумент интерпретируется как длинный double (применяется только к спецификаторам с плавающей точкой — e, E, f, g и G).
Структура проекта
Проект имеет модульную структуру для лучшей организации кода.
└── StringPlus/ # Репозиторий с исходным кодом и ресурсами
├── resources/ # Файлы, используемые в документации
│ └── stringplus.png # Главное изображение
├── tests/ # Директория с модульными тестами
│ ├── test.c # Основной модуль запуска тестов
│ ├── test.h # Заголовочный файл
│ ├── ... # Модульные тесты для функций библиотеки
│ └── test_trim.c # Модульные тесты для функции trim
├── format_specifier/ # Модуль для работы со спецификотором формата функций sprintf() и sscanf()
│ ├── specifier_handler.c # Применение форматирования к переданному аргументу
│ ├── specifier_handler.h # Заголовочный файл
│ ├── specifier_parser.c # Разбор строки форматирования на составляющие \[флаги\]\[ширина\]\[.точность\]\[длина\]спецификатор
│ └── specifier_parser.h # Заголовочный файл
├── my_string.h # Заголовочный файл с объявлениями функций
├── my_string.h # Заголовочный файл с определением size_t и NULL
├── my_sscanf.c # Реализация sscanf
├── my_sprintf.c # Реализация sprintf
├── my_insert # Реализация insert
├── my_memchr # Реализация memchr
├── my_memcpy # Реализация memcpy
├── my_memcmp # Реализация memcmp
├── my_memcpy # Реализация memcpy
├── my_memset # Реализация memset
├── my_strchr # Реализация strchr
├── my_strcspn # Реализация strcspn
├── my_strerror # Реализация strerror
├── my_strncat # Реализация strncat
├── my_strpbrk # Реализация strpbrk
├── my_strrchr # Реализация strrchr
├── my_strstr # Реализация strstr
├── my_strtok # Реализация strtok
├── my_to_lower # Реализация to_lower
├── my_to_upper # Реализация to_upper
├── my_trim # Реализация trim
├── Makefile # Управление сборкой
└── README.md # Документация на русском
Установка и сборка
Для сборки проекта требуется make и компилятор gcc.
Клонируйте репозиторий:
git clone [ссылка на РЕПОЗИТОРИЙ]
Цели Makefile
Основные цели сборки
Данный проект собирается в виде статической библиотеки my_string.a. Модуль тестирования собирается и запускается командами make all или make test. Отчет о тестировании заносится в файл test_report.log, который генерируется автоматически при запуске указанных команд.
Для запуска тестирования необходимо установить библиотеку Check, например для Ubuntu:
sudoaptinstallcheck
Для формирования отчета о тестировании необходимо установить gcov, например для Ubuntu:
sudoaptinstallgcov
Команда
Описание
make all
Сборка библиотеки и запуск тестов
make library
Сборка статической библиотеки my_string.a
make test
Сборка библиотеки и запуск тестов
make gcov_report
Сборка библиотеки и запуск тестов с выпуском отчета о тестировании
make view-report
Выполнение цели gcov_report и открытие отчета о тестировании
make clean
Очистка сборки
Проверка кода
Для форматирования кода потребуется clang-format, исходные настройки стиля (.clang-format) прилагаются к проекту. Для статического анализа кода потребуется cppcheck (2.7).
Команда
Описание
make format
Форматирование кода clang-format
make check-format
Проверка стиля кода
make cppcheck
Статический анализатор кода
Проверка программы
Для проверки утечек памяти потребуется valgrind (3.18.1).