Форум программистов, компьютерный форум, киберфорум
C для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.75/4: Рейтинг темы: голосов - 4, средняя оценка - 4.75
0 / 0 / 0
Регистрация: 17.08.2017
Сообщений: 30
1

Запись данных из файла в связанный список

12.11.2018, 00:26. Показов 676. Ответов 3

Author24 — интернет-сервис помощи студентам
Здравствуйте,
нужно выгрузить данные про песни (название, год, альбом итд) из файла в связнный список. Каждая одна песня- список. В файл они были загружены тоже с помощью списка. Но я теперь не знаю как из файла выгрузить данные в виде списка а потом знать указатель на первый элемент.
Вот код, который я попробовала написать
C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
void loaddb(void){
for (;;)
    {
    list *head;
    FILE *f;
    printf("\ntransfer the database file in one folder with program and enter the name of the database file\n");
    scanf("%s",fname);
    printf("\n Your entered: %s", fname);
    f=fopen(fname, "r+");
    if(f==NULL)  {printf(" file does not exist");}
    else {printf("  file opened ");
    list *head=NULL;
    while ( feof (f) == 0) {
          if (head==NULL)
          {list *p=(list*)malloc(sizeof(list));
          p->next=head;
          fscanf(f, "Song title: %s \tAlbum: %s\tYear: %d\tGenre:%s \tLength (min, sec) %d:%d \tArtist: %s\tbelong to pl: %d\tID: %p\r\n",p->data.title,p->data.album,&p->data.year,p->data.genre,&p->data.length.min, &p->data.length.sec, p->data.artist,&p->data.pl,p->data.id);
          }
          else {
          list *p;
          for (p=head; p->next != NULL; p=p->next){
          p->next=(list*)malloc(sizeof(list));
          p->next->next=NULL;
          fscanf(f, "Song title: %s \tAlbum: %s\tYear: %d\tGenre:%s \tLength (min, sec) %d:%d \tArtist: %s\tbelong to pl: %d\tID: %p\r\n",p->next->data.title,p->next->data.album,&p->next->data.year,p->next->data.genre,&p->next->data.length.min, &p->next->data.length.sec, p->next->data.artist,&p->next->data.pl,p->next->data.id);
}
          }
    }
 
    if (ferror(f))
        printf("err\n");
     }
 
    printf("\nTo return to the main menu press 'a', to exit from the program press 'b', to repeat press any other character\n");
    char choice;
    scanf(" %c", &choice);
    if (choice == 'a')
            main_menu(head);
    else if (choice == 'b')
            exit(0);
    }
}
Знаю, наверное много косяков, но помогите, пожалуйста, как это можно правильно написать?
В файле каждая песня разделена вот этим \r\n . Выглядит подобным образом:
Song title: One Album: One Year: 1 Genre:one Length (min, sec) 1:1 Artist: one belong to pl: 1 ID: 00B40D48
Song title: two Album: two Year: 2 Genre:two Length (min, sec) 2:2 Artist: two belong to pl: 0 ID: 00B40E18
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
12.11.2018, 00:26
Ответы с готовыми решениями:

Выгрузка данных из файла в связанный лист: непонятный элемент
Здравствуйте, я пытаюсь выгрузить данные из файла про песни в связанный список. В файле каждый...

Запись в связный список из файла
Описание списков: typedef struct name { char first_name; char last_name; int...

Сформировать циклический связанный список (очередь)
Сформировать циклический связанный список (очередь), содержащий последовательность целых чисел,...

Построить в динамической памяти линейный связанный список строкового типа данных
Задание: Построить в динамической памяти линейный связанный список строкового типа данных....

3
Невнимательный
2683 / 1101 / 345
Регистрация: 08.02.2013
Сообщений: 6,270
Записей в блоге: 2
12.11.2018, 04:58 2
Вы пробовали, как работают эти fsprintf ? В названиях могут быть пробелы?
Пробую запустить на скопированых отсюда строках, из-за этого слегка изменил формат, и всё-равно не могу вывести
, .data.artist это крайнее что я смог получить, и то если заменяю это %s
C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
#include <stdio.h>
#include <string.h>
 
typedef struct {
    struct {
        char title[128], album[128];
        int year;
        char genre[4];
        struct {
            int min, sec;
        } length;
        char artist[80];
        int pl;
        void* id;
    } data ;
    void* next;
} list;
 
list bp[2];
 
int main(){
    int i, n=0;
    list *p = bp;
    FILE* f=fopen("test.txt", "r+");
 
    do {
    i = fscanf(f, "Song title: %s Album: %s Year: %d Genre: %s Length (min, sec) %d:%d Artist: %[ A-Za-z] belong to pl: %d ID: %p ",p->data.title,p->data.album,&p->data.year,p->data.genre,&p->data.length.min, &p->data.length.sec, p->data.artist,&p->data.pl,p->data.id);
    //getchar();
    } while(!feof(f) && i && ++n);
 
    for (i=0;i<n; ++i){
        printf("%s %s %d %s %d %d %s\n"// %d %x
            , bp[i].data.title, bp[i].data.album, bp[i].data.year, bp[i].data.genre
            , bp[i].data.length.min, bp[i].data.length.sec
            , bp[i].data.artist /*,bp[i].data.pl,bp[i].data.id*/);
    }
    return 0;
}
может у меня другая структура, или всё дело в том что \t отсюда не копируется?
0
0 / 0 / 0
Регистрация: 17.08.2017
Сообщений: 30
13.11.2018, 02:04  [ТС] 3
Да в названиях могут быть пробелы,
но я не знаю по какому принципу сканф читает в структуру, для меня это просто не понятно. В смысле, например, я сделала по той логике, что просто копирую слова, которые мне не нужны в структуре (как Song title, а нужные данные заменяю на %s это правильно? Спасибо за ответ
0
724 / 224 / 72
Регистрация: 01.03.2011
Сообщений: 629
13.11.2018, 07:51 4
Цитата Сообщение от Lara Semenova Посмотреть сообщение
а нужные данные заменяю на %s это правильно?
Т.к в названиях могут быть пробелы - неправильно.
%s прекращает парсинг наткнувшись на 1й же пробел (на любой символ для которого isspace() возвращает не 0) Используйте %[] как вы сделали для поля Artist, но с ограничением максимального размера.
C
1
parsed = fscanf(f, "Song title: %" SONG_TITLE_MAX - 1 "[^\t]Album: %" ALBUM_MAX - 1 "[^\t]"...
После проверять, что fscanf() вернула верное число, проверять все возможные поля на правильность - например вменяемый год, секунд не больше 59 и тд

Но вообще, я бы посоветовал использовать fgets() для чтения строки целиком, и после проверок типа строка прочитана полностью, не превышает макс. размер, не пустая, и тп. парсил бы руками, ну или sscanf() на худой конец.
1
13.11.2018, 07:51
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
13.11.2018, 07:51
Помогаю со студенческими работами здесь

Линейно-связанный список: вывести список положительных и отрицательных чисел
Дано неотрицательное N и набор из N чисел. Создать линейно-связанный список, содержащий исходные...

Связанный список. Создать, записать в связный список последовательность слов,обозначающих месяцы года,заданных пользователем
Создать связанный список.Кроме информационных полей он должен обязательно содержать указатели на...

Связанный список
Есть таблица состоящая из двух столбцов(максимум 100 строк) на листе1. Пусть это будут столицы...

Связанный список
Не могу обратиться к методу класса Node хотя они выраженны как public: void addNode(int d); void...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
4
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru