Здравствуйте, возникла проблема при выполнении программы.
#include <conio.h>
#include <stdio.h>
#include <stdlib.h>
#include <memory.h>
struct Customer {
char fio[20]; // ФИО покупателя
int id; // порядковый номер
char address[20]; // адрес покупателя
char delivDate[20]; // дата доставки
struct Customer *next; //следующий покупатель
};
typedef struct Customer *PCust; // массив структур
PCust CreateCustomer(char *NewFio, char *NewAdress, char *NewData, int id);
PCust Find(PCust Head, char NewFio[]);
void AddFirst(PCust * Head, PCust NewCustomer);
void AddLast(PCust *Head, PCust NewCustomer);
void AddAfter(PCust p, PCust NewCustomer);
void DeleteNode(PCust *Head, PCust p);
...
int main() {
while (1)
switch (menu())
{
case 1:newList(); break;
case 2:readFromFile(); break;
case 3:addCustomer(); break;
case 4:deleteCustomer(); break;
case 5:changeCustomerField(); break;
case 6:searchInCustomers(); break;
case 7:return 0;
default:printf("Neverniy vibor\n");
}
}
int menu()
{
int choice;
do
{
//system("cls");
printf("Menu\n");
printf("1.New list\n");
printf("2.Read from file\n");
printf("3.Add customer\n");
printf("4.Delete customer\n");
printf("5.Change customer field\n");
printf("6.Search in customers\n");
printf("7.Exit\n");
printf("Vash vibor?\n");
scanf_s("%d", &choice);
//system("cls");
} while (choice>7);
return choice;
}
void addCustomer(void) {
PCust Head = NULL;
struct Customer currentCustomer;
printf("Vvedite FIO pokupatelya: ");
scanf("%s", currentCustomer.fio);
printf("Vvedite datu dostavki: ");
scanf("%s", currentCustomer.delivDate);
printf("Vvedite adres pokupatelya: ");
scanf("%s", currentCustomer.address);
printf("Vvedite nomer pokupatelya: ");
scanf("%d", ¤tCustomer.id);
PCust customerNode = CreateCustomer(currentCustomer.fio, currentCustomer.address,
currentCustomer.delivDate, currentCustomer.id);
AddLast(&Head, customerNode);
// writeToFile(&customerNode);
}
void writeToFile(PCust *Head) {
// FILE *f;
// f=fopen("customers.txt", "w");
PCust q = *Head; // Начали с головы
if (*Head == NULL)
return;
while (q->next) // Пока не дошли до конца
{
printf("%s\n", q->fio);
printf("%d\n", q->id);
printf("%s\n", q->address);
printf("%s\n", q->delivDate);
// q = q->next; // Переходим к следующему узлу
}
printf("Vishli");
// fclose(f);
}
PCust CreateCustomer(char *NewFio, char *NewAdress, char *NewData, int id){
PCust NewCustomer = (PCust)malloc(sizeof(PCust));
strcpy(NewCustomer->fio, NewFio);
strcpy(NewCustomer->address, NewAdress);
strcpy(NewCustomer->delivDate, NewData);
NewCustomer->id = id;
NewCustomer->next = NULL;
return NewCustomer;
}
// Добавление нового узла
void AddFirst(PCust * Head, PCust NewCustomer){
NewCustomer->next = *Head;
Head = &NewCustomer;
}
// Добавление узла между элементами
void AddAfter(PCust p, PCust NewCustomer){
NewCustomer->next = p->next;
p->next = NewCustomer;
}
// Добавить узел в конец списка
void AddLast(PCust *Head, PCust NewCustomer){
PCust q = *Head;
// Если список пустой
if (*Head == NULL)
{
AddFirst(Head, NewCustomer);
return;
}
// Цикл прохода до последнего узла списка
while (q->next)
q = q->next;
// Добавление узла после заданного узла,
// в данном случае после q
AddAfter(q, NewCustomer);
}
Я использую односвязный список и при добавлении клиента (функция addCustomer()), выдает ошибку:
Exception thrown at 0x77466EDD (ntdll.dll) in CourseWork_Test.exe: 0xC0000005: Access violation reading location 0x00000003.
указывая на строку
PCust NewCustomer = (PCust)malloc(sizeof(PCust));
Ошибка появляется при добавлении второго или третьего клиента.
Скриншот вывода программы:
Спасибо
Совершенно не понятно, чего вы пытаетесь добиться создавая списки для локального указателя Head
в каждой из своих функций типа addCustomer
и никак не возвращая его наружу. Как эти функции собираются общаться между собой (а по замыслу они должны общаться между собой) - не ясно.
Что касается падения, то налицо популярная ошибка
PCust NewCustomer = (PCust)malloc(sizeof(PCust));
вызванная типичными и легко узнаваемыми "манерами" низкокачественного кода. В данном случае - использование имени типа под sizeof
и сокрытие указательного типа под typedef
У вас PCust
- это тип-указатель. Соответственно ваш malloc(sizeof(PCust))
выделяет память под один указатель, а не под структуру struct Customer
. Вам нужно sizeof(struct Customer)
байтов памяти, а не sizeof(PCust)
.
Как минимум исправьте размер в этом malloc
.
А лучше - уберите из кода нафиг тип PCust
- не надо скрывать указательные типы под typedef
именами (это бывает полезно, но отнюдь не в таких контекстах). Сделайте typedef
на struct Customer
, если вам так уж хочется более короткой записи
typedef struct Customer Customer;
И научитесь пользоваться идиомой
T *p = malloc(sizeof *p);
В вашем случае
Customer *NewCustomer = malloc(sizeof *NewCustomer);
Также отдельная белиберда написана в AddFirst
. Должно быть
void AddFirst(PCust * Head, PCust NewCustomer){
NewCustomer->next = *Head;
*Head = NewCustomer;
// а не `Head = &NewCustomer`
}
Кофе для программистов: как напиток влияет на продуктивность кодеров?
Рекламные вывески: как привлечь внимание и увеличить продажи
Стратегії та тренди в SMM - Технології, що формують майбутнє сьогодні
Выделенный сервер, что это, для чего нужен и какие характеристики важны?
Современные решения для бизнеса: как облачные и виртуальные технологии меняют рынок
Приветствуюподскажите, есть обычная форма подписки и есть всплывающее окно при уходе с сайта
Пытаюсь расширить класс Array при помощи prototype, добавив в него свой метод, но при обходе массива циклом созданный метод видится элементом массива: