Слайд 1Язык С
Лекция №5
Структуры данных
Слайд 2Типы данных, определяемые пользователем
Структуры
Битовые структуры
Объединения
Перечисления
Слайд 3Структуры
Определение структуры
struct student
{ char name[32];
int year;
int marks[10];};
Описание
переменных
struct student stud1, stud2;
student stud3;
Работа
stud1.name="Petrov";
stud2=stud1;
Слайд 4Структуры
Структура без имени
struct
{ char name[32];
int year;
int marks[10];} s;
Переопределение
типа
typedef struct student
{ char name[32];
int year;
int marks[10];} STUDENT;
Слайд 5Указатели на структуру
typedef STUDENT* PSTUDENT;
PSTUDENT p, q;
p=(PSTUDENT) malloc(sizeof(STUDENT));
(*p).year=1990;
p->year =1990;
Слайд 6Функции для работы со структурой
void setstudent(PSTUDENT p, char *name,
int year)
{
strcpy(p->name,name);
p->year=year;
for (int i=0; i<10; i++) p->marks[i]=0; }
PSTUDENT createstudent(char *name, int year)
{
PSTUDENT p;
p= (PSTUDENT ) malloc(sizeof(STUDENT ));
setstudent(p,name,year);
return p; }
main ()
{ STUDENT s;
PSTUDENT p;
setstudent(&s,"Alexey",1990);
p=createstudent("Alexander",1980); }
Слайд 7Дополнительные возможности
Доступ к битам
struct byte { int b1 : 1;
int b2 : 1;
int b38: 6; };
Объединения
union bits { char ch;
struct byte b; } u;
u.ch='A'; printf("%d",u.b.b1);
Перечислимый тип
enum value {zero, one, two, ten=10, eleven, twenty=20} v;
Слайд 8Примеры на union
struct person
{ char name[32];
char status;
union { long int n[5];
short int m[10];
};
};
person a, b;
…
If (a.status==‘F’) a.n[0]=29842391;
else a.m[0]=0;
Слайд 9Использование битовых флагов
#define math 1
#define cpp 2
#define sql
4
#define python 8
…
int zach;
zach = zach | math |
sql;
if (zach & math) printf("math!");
zach &= !math;
Слайд 11Стек
/* Работа со стеком */
#include
#include
#include
#include
typedef struct
stack STACK;
typedef STACK* PSTACK;
struct stack
{ int data;
PSTACK
prev; };
PSTACK p=NULL; // вершина стека
Слайд 12Стек
void push(int x) // добавить в стек
{ STACK *q;
q=malloc(sizeof(STACK));
q->prev=p;
q->data=x;
p=q;
}
int peek() //
{if (p==NULL) return 0;
else return
p->data;
}
Слайд 13Стек
int pop() // снять с вершины
{ STACK *q;
int x;
if (p==NULL) return 0;
q=p;
x=q->data;
p=q->prev;
free(q);
return x;
}
int
find (STACK *p, int x) // рекурсивный поиск
{ if (p==NULL) return 0;
if (p->data==x) return 1;
return find(p->prev,x);
}
Слайд 14void main()
{char c;
int z;
do
{ printf("\npUsh, Pop, Find,
Quit ->");
c=toupper(getche());
switch (c)
{
case 'U': printf("\nValue->");
scanf("%d",&z);
push(z);
break;
case 'P': if (z=pop()) printf("\nValue=%d",z);
else printf("\nStack is empty!");
break;
case 'E': if (z=peek()) printf("\nValue=%d",z);
else printf("\nStack is empty!");
break;
case 'F': printf("\nValue->");
scanf("%d",&z);
if (find(p,z)) printf("\nElement is found.");
else printf("\nElement is not found!");
break;
}
} while ((c!=0x1B) && (c!='Q'));
}
Слайд 16Реализация двоичного дерева
typedef struct tree
{ int data;
TREE
*left;
TREE *right; } TREE;
Слайд 17Домашнее задание
Написать функцию вставки значения в «правильное» положение
Написать функцию поиска
(есть или нет) в дереве значения
Слайд 19Работа с файловой системой в языке С
Слайд 20Структура FILE
typedef struct{
short level;
unsigned
flags;
char
fd;
unsigned char hold;
short bsize;
unsigned char *buffer, *curp;
unsigned istemp;
short token;
} FILE;
Слайд 21Открытие/закрытие файла
FILE *fopen(const char *filename, const char *mode);
int fclose(FILE
*stream);
r Только для чтения.
w Создать для записи, если существует, то создать
заново
a Дописывать в существующий или создать.
r+ Открыть существующий для чтения и изменения.
w+ Создать новый файл для чтения и изменения.
a+ Открыть файл для изменения, но позиционировать в конец
FILE * in;
in = fopen("AUTOEXEC.BAT", "rt"));
fclose(in);
Слайд 22Позиционирование файла
int fseek(FILE *stream, long offset, int whence)
SEEK_SET 0 с начала
файла
SEEK_CUR 1 от текущей позиции
SEEK_END 2 с конца файла
void rewind(FILE *stream) – перемотать
long int
ftell(FILE *stream) – вернуть указатель
int feof(FILE *stream) – вернуть ситуацию «конец файла»
Слайд 23Простейший ввод/вывод
int fputc(int c, FILE *stream) – вывести символ
int fgetc(FILE
*stream) – прочитать символ
char *fgets(char *s, int n, FILE *stream)
– прочитать строку
int fputs(const char *s, FILE *stream)
– вывести строку
Слайд 24Форматный ввод/вывод
int fprintf(FILE *stream,
const
char *format[, argument, ...])
int fscanf(FILE *stream,
const char *format[, address, ...])
fprintf(f,"%s %d","Message ",n);
fscanf(in,"%d %d",&n,&m);
Слайд 25Бинарный ввод/вывод
size_t fwrite(const void *ptr,
size_t size, size_t n,
FILE *stream);
– вывод n объектов размером size, ptr указывает на объект
size_t fread(void *ptr,
size_t size, size_t n,
FILE *stream);
– чтение n объектов по size байт
Слайд 26Операции с файлами
int remove(const char *filename);
– удалить файл
int rename(const
char *oldname,
const char *newname);
– переименовать
Слайд 27Пример программы
/* Program to create backup of the AUTOEXEC.BAT file
*/
#include
int main(void)
{ FILE *in, *out;
if ((in =
fopen("\\AUTOEXEC.BAT", "rt")) == NULL)
{ fprintf(stderr, "Cannot open input file.\n");
return 1; }
if ((out = fopen("\\AUTOEXEC.BAK", "wt"))== NULL)
{ fprintf(stderr, "Cannot open output file.\n");
return 1; }
while (!feof(in))
fputc(fgetc(in), out);
fclose(in);
fclose(out);
return 0;
}
Слайд 28Пример бинарного ввода-вывода
#include
struct mystruct {int i;
char ch; };
int main(void)
{
FILE *stream;
struct mystruct s;
if ((stream = fopen("TEST.$$$", "wb")) == NULL)
{
fprintf(stderr, "Cannot open output file.\n");
return 1;
}
s.i = 0; s.ch = 'A';
/* запись структуры s в файл */
fwrite(&s, sizeof(s), 1, stream);
fclose(stream);
return 0;
}