Списки
Помогите разобратьс списком ..
#include <stdlib.h>
const int k=5;
struct spisok
{
char name[3]; /* элемент списка */
struct spisok *next ; /* указатель на последующий элемент*/
} info;
struct spisok *last;//последний
int vvod(struct spisok *i ,struct spisok **last )
{
if (!*last) *last = i;
else (*last)->next = i;
i->next = NULL;
*last = i ;
}
int main()
{
// struct spisok info =NULL;
last =NULL;
struct spisok *info=NULL;
int i;
for (i=0;i<k;i++){
printf("Enter:\n");
scanf("%c",info->name);
vvod(info, &last);
info = (struct spisok *) malloc(sizeof(struct spisok));
if (!info){
printf("\n Нет свободной памяти");
return;
}
}
}
При компиляции исходник отказывается работать . -
пишет следующее..
(gdb) run
Enter:
Program received signal SIGSEGV, Segmentation fault.
0x080484a8 in vvod ()
непонимаю в чем ошибка ....
ps:/предчувствую ..что maloc не правильно работает .. но не понимаю как заставить его иначе
Помогите разобратьс списком ..
#include <stdlib.h>
const int k=5;
struct spisok
{
char name[3]; /* элемент списка */
struct spisok *next ; /* указатель на последующий элемент*/
} info;
struct spisok *last;//последний
int vvod(struct spisok *i ,struct spisok **last )
{
if (!*last) *last = i;
else (*last)->next = i;
i->next = NULL;
*last = i ;
}
int main()
{
// struct spisok info =NULL;
last =NULL;
struct spisok *info=NULL;
int i;
for (i=0;i<k;i++){
printf("Enter:\n");
scanf("%c",info->name);
vvod(info, &last);
info = (struct spisok *) malloc(sizeof(struct spisok));
if (!info){
printf("\n Нет свободной памяти");
return;
}
}
}
При компиляции исходник отказывается работать . -
пишет следующее..
(gdb) run
Enter:
Program received signal SIGSEGV, Segmentation fault.
0x080484a8 in vvod ()
непонимаю в чем ошибка ....
ps:/предчувствую ..что maloc не правильно работает .. но не понимаю как заставить его иначе
Вот по рукам вам за такое "понадавать" надо бы:
printf("Enter:\n");
scanf("%c",info->name);
vvod(info, &last);
info = (struct spisok *) malloc(sizeof(struct spisok));
if (!info){
printf("\n Нет свободной памяти");
return;
}
}
Вы пытаетесь что-то записать в недоступную память, на которую ссылается указатель info.
Нужно так:
printf("Enter:\n");
info = (struct spisok *) malloc(sizeof(struct spisok));
if (!info){
printf("\n Нет свободной памяти");
return -1;
}
scanf("%c",info->name);
vvod(info, &last);
}
return 0;
P.S. Логические ошибки, если они есть конечно, ищите и исправляйте сами.
С этого началась проблема ..
При запуске вводится всего 3 элемента,хотя k =5 -> ниже видно ,что функция выполняется 5 раз (По колличеству Enter:)
(gdb) run
Enter:e
Enter:
Enter:r
Enter:
Enter:t
Не понятно .. как массив char name[3] может повлиять ...)
Если указать просто char name (не как массив .. )то фукция просто распечатывает Enter : ...ошибка при записи в структуру и создании нового елемента
#include <stdlib.h>
const int k=5;
struct spisok
{
char name[3]; /* элемент списка */
struct spisok *next ; /* указатель на последующий элемент*/
} info;
struct spisok *last;//последний
int vvod(struct spisok *i ,struct spisok **last )
{
if (!*last) *last = i;
else (*last)->next = i;
i->next = NULL;
*last = i ;
}
int main()
{
last =NULL;
struct spisok *info=NULL;
int i;
for (i=0;i<k;i++){
printf("Enter:\n");
info = (struct spisok *) malloc(sizeof(struct spisok));
if (!info){
printf("\n Нет свободной памяти");
return -1;
}
scanf("%c",info->name);
vvod(info, &last);
}
return 0;
Во-вторых, этот код чреват переполнением буфера.
В-третьих, занятую память нужно освобождать. Где free ?
[COLOR="gray"]P.S. Итить-колотить, второе десятилетие двадцать первого века! А программы по-прежнему текут памятью и переполняют буфера.
Наболело...[/COLOR]
2 ) Поэтому тема была создана .. потому-что афтару не дошло понимание того как с этим бороться
3 ) struct spisok *info=NULL; разве это не равносильно free ?
P.S: ...в ожидании пинка к пути правильного решения..=)
#include <stdlib.h>
const int k=5;
struct spisok
{
char name[3]; /* элемент списка */
struct spisok *next ; /* указатель на последующий элемент*/
} info;
struct spisok *last [COLOR="#8b0000"]= NULL[/COLOR];//последний
[COLOR="red"]int vvod(struct spisok *i )[/COLOR]
{
if (last==NULL)
last = i;
else
{
last->next = i;
i->next = NULL;
last = i ;
//Составной оператор был неверно определен
}
}
//Почему функция не void?
int main()
{
struct spisok *info;
//NULL можно опустить
for (int i=0;i<k;i++){
printf("Enter:\n");
info = (struct spisok *) malloc(sizeof(struct spisok));
if (!info){
printf("\n Нет свободной памяти");
return -1;
}
scanf("%c",info->name);
[COLOR="red"] vvod(info);[/COLOR]
//Смысл передавать в функцию глобальную переменную?!
}
return 0;
}
Попробуй вот так, хотя за корректность не ручаюсь. На Си не пишу, только на С++ пока
3 ) struct spisok *info=NULL; разве это не равносильно free ?
Никак нет! Таким образом только затирается указатель на выделенную память.
Выделенная память же остаётся закреплённой за процессом, и недоступна другим.
Мне необходимо решить контрольную
Задание:
Структура данных – двусвязная, на базе массива с индексными указателями
Нашел в инете статью: http://www.rsdn.ru/article/alg/list.xml
но в ней пример на Visual Basic 6.0
Не могу найти пример на C++ для понимания данной задачи.
Почему сразу лодыри?
Я не специалист по C++, только начинаю.
Вместо того чтобы оскорблять человека, поделились бы опытом или ссылкой.
Когда же человек говорит - мне это надо, но я в этом не понимаю иначе как лодырем не назовешь, уж извините.
Когда же человек говорит - мне это надо, но я в этом не понимаю иначе как лодырем не назовешь, уж извините.
Я не прошу делать задачу за меня.
Я прошу пример реализации списка на базе массива с индексными указателями.
Или ссылку на источник где можно посмотреть.
Я прошу пример реализации списка на базе массива с индексными указателями.
А вы видите разницу между этим?
#include <stdlib.h>
#include <string.h>
#define SYMS_IN_STRUCT 3
int k=5;
struct spisok
{
char name[SYMS_IN_STRUCT]; /* элемент списка */
struct spisok *prev; /* указатель на предыдущий элемент*/
struct spisok *next; /* указатель на следующий элемент*/
};
struct spisok *first=NULL; /* первый */
struct spisok *last=NULL; /* последний */
void add_record(struct spisok *i)
{
if(!first)first=i;
if (!last){last=i;i->prev=NULL;}
else {last->next=i; i->prev=last; last=i;}
i->next=NULL;
}
int main(int argc, char **argv)
{
struct spisok *info;
int i;
char tmps[32];
char ofmt[32];
printf("Number of elements [5] : ");
fgets(tmps, 30, stdin);
k=atoi(tmps);
if(k<1) k=5;
sprintf(ofmt, "[%%u]=%%.%us\n", SYMS_IN_STRUCT); /* Создаём строку формата */
for (i=0;i<k;i++){
printf("Enter: ");
fgets (tmps, SYMS_IN_STRUCT+2, stdin);
if(!(info = (struct spisok *)malloc(sizeof(struct spisok))))
{printf("Нет свободной памяти! \n"); return -1;}
memcpy((void*)&(info->name), (void*)tmps, SYMS_IN_STRUCT);
add_record(info);
}
/* --- Вывод --- */
info=first;
i=1;
do{
printf(ofmt, i, &(info->name));
info=info->next; i++;
}while(info);
/* --- Освобождение памяти --- */
info=last;
do{
if(info->prev) {info=info->prev; free((void*)(info->next));}
else {free((void*)info); info=NULL;}
}while(info);
return 0;
}
:facepalm::facepalm:
Да ничего страшного. :) А то, если сделать typedef struct {...} spisok; - не получится объявить исходный тип внутри структуры.
Для себя я делаю в таких случаях члены структуры типа void*. А раз ТС захотел так, то и пусть будет. Это не принципиально.
Да что вы говорите?..Вот кусок кода из рабочей программы
struct tag ## Type ## List{\
Type v ## Type;\
struct tag ## Type ## List *pNext;\
}
typedef TypeList(Node) NodeList;
typedef TypeList(Elt) EltList;
typedef TypeList(Disp) DispList;
typedef TypeList(Load) LoadList;
Но опять же внутри структуры объявления типа struct Type, а не просто Type. :)
И как результат, в программе фигурируют два типа.
int vSomeVal;
SomeType *pvSomeType;
}SomeType;
Естественно, надо:
[code=c++]
struct spisog
[/code]
int vSomeVal;
SomeType *pvSomeType;
}SomeType;
Вот это уже не будет компилиться. В чистом C по крайней мере. А у ТС именно он. Прверил в PelesC, tcc, gcc.