Форум программистов, компьютерный форум, киберфорум
C++ Builder
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.50/4: Рейтинг темы: голосов - 4, средняя оценка - 4.50
1 / 1 / 2
Регистрация: 07.04.2012
Сообщений: 38
1

Ошибка при выводе бинарного файла

07.04.2012, 15:14. Показов 795. Ответов 4
Метки нет (Все метки)

Добрый день!
Ошибка вот в чем: при сортировке массива, в одну ячейку StringGrid вставляет две переменные. И из-за этого наверно теряется одна строка файла. Вот скрин проблемы.
http://savepic.net/2743341.htm
Исходный код, вот:
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
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
#include <vcl.h>
#pragma hdrstop
#include <stdio.h>
#include <DateUtils.hpp>
#include "Unit1.h"
#include "bibl.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
int n=0;
//FILE *f2;
//---------------------------------------------------------------------------
 
void setka1(TStringGrid *sg)
{sg->Cells[0][0]="№";
sg->Cells[1][0]="Марка авто";
sg->Cells[2][0]="Производитель";
sg->Cells[3][0]="Тип";
sg->Cells[4][0]="Год выпуска";
sg->Cells[5][0]="Дата регистрации";
}
 
void setka2(TStringGrid *sg,int i)
{sg->Cells[1][i+1]=AnsiString(a.mark);
sg->Cells[2][i+1]=AnsiString(a.pr);
sg->Cells[3][i+1]=AnsiString(a.tip);
sg->Cells[4][i+1]=AnsiString(a.god);
sg->Cells[5][i+1]=AnsiString(a.d);
}
 
//Запись в файл
void __fastcall TForm1::Button1Click(TObject *Sender)
{
f1=fopen("avto.dat","ab+");
strcpy(a.mark,Edit1->Text.c_str());
strcpy(a.pr,Edit2->Text.c_str());
strcpy(a.tip,ComboBox1->Text.c_str());
strcpy(a.god,Edit3->Text.c_str());
strcpy(a.d,Edit4->Text.c_str());
fwrite(&a,sizeof(a),1,f1);
n++;
fclose(f1);
}
//---------------------------------------------------------------------------
//Просмотр файла
void __fastcall TForm1::Button2Click(TObject *Sender)
{
setka1(sg1);
int i=0;
f1=fopen("avto.dat","rb+");
while(fread(&a,sizeof(a),1,f1)>0)
{setka2(sg1,i);
i++;}
for(int j=1;j<=n;j++)
sg1->Cells[0][j]=IntToStr(j);
sg1->RowCount=i+1;
fclose(f1);
}
 
//---------------------------------------------------------------------------
// Сортировка массива
void __fastcall TForm1::Button4Click(TObject *Sender)
{
setka1(sg3);
int i,k=kol(f1);
avto *mas=new avto[k];
formir(f1,mas,k);
sort(mas,k);
for(i=0;i<=k;i++)
{sg3->Cells[1][i+1]=AnsiString(mas[i].mark);
sg3->Cells[2][i+1]=AnsiString(mas[i].pr);
sg3->Cells[3][i+1]=AnsiString(mas[i].tip);
sg3->Cells[4][i+1]=AnsiString(mas[i].god);
sg3->Cells[5][i+1]=AnsiString(mas[i].d);
}
{setka2(sg3,i);
i++;}
for(int j=1;j<=k;j++)
sg3->Cells[0][j]=IntToStr(j);
sg3->RowCount=k;
}
Вот библиотека bibl.cpp:

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
#pragma hdrstop
#include <stdio.h>
#include <DateUtils.hpp>
#include "bibl.h"
#pragma package(smart_init)
 
int kol(FILE *f1)
{int k=0;
f1=fopen("avto.dat","rb");
fseek(f1,0,2);
k=ftell(f1)/sizeof(a);
fclose(f1);
return k;
}
 
void formir(FILE *f1,avto mas[],int n)
{f1=fopen("avto.dat","rb");
for(int k=0;k<n;k++)
{fread(&a,sizeof(a),1,f1);
mas[k]=a;}
fclose(f1);
}
 
void sort(avto mas[],int k)
{int i,j;
avto z;
for(i=0;i<=k;i++)
for(j=i+1;j<k-1;j++)
if((AnsiString)mas[i].god<(AnsiString)mas[j].god)
{(avto)z=(avto)mas[i];
(avto)mas[i]=(avto)mas[j];
(avto)mas[j]=(avto)z;}
}
И bibl.h:
C++
1
2
3
4
5
6
7
8
9
#ifndef biblH
#define biblH
struct avto{char mark[20];char pr[15];char tip[10];char god[15];char d[10];}a;
FILE *f1;
 
int kol(FILE *f1);
void formir(FILE *f1,avto mas[],int n);
void sort(avto mas[],int k);
#endif
Заметил также, что в бинарный файл данные записываются без пробела, т.е. вот так:
"Toyota Япония Легковая 2007 12.05.2006Toyota Япония Легковая 2006 12.05.2006"

Может стоит поставить пробел при записи в бинарный файл? Если да, подскажите как.
Спасибо.

P.S. Задаю вопрос первый раз, если что не так прошу не ругать)))
0

Помощь в написании контрольных, курсовых и дипломных работ здесь.

Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
07.04.2012, 15:14
Ответы с готовыми решениями:

Ошибка при чтении бинарного файла
пытаюсь прочитать 63мб бинарного файла и заполнить структуру к примеру вот std::fstream...

Ошибка при выводе содержимого бинарного файла
#include &quot;stdafx.h&quot; #include &quot;windows.h&quot; #include &lt;iostream&gt; #include &lt;fstream&gt; using...

Ошибка в выводе Бинарного дерева
В бинарном дереве выдается корявый вывод: элементы, которые идут в правом листе в начале пишется...

Ошибка при вводе - выводе из файла
Почему пишет не найдет файл (в проге ассигн,ресет, реврайт стоит на него) создаю его вручную -...

4
Практикантроп
4682 / 2601 / 497
Регистрация: 23.09.2011
Сообщений: 5,584
07.04.2012, 21:30 2
Цитата Сообщение от Pavel_n Посмотреть сообщение
Если да, подскажите как.
Увеличьте значение поля d (у Вас 10 - это впритык: 11.11.2012 - десять символов) или добавьте пустое поле (пробел) в структуру после d.
1
1 / 1 / 2
Регистрация: 07.04.2012
Сообщений: 38
08.04.2012, 01:15  [ТС] 3
Цитата Сообщение от nick42 Посмотреть сообщение
Увеличьте значение поля d (у Вас 10 - это впритык: 11.11.2012 - десять символов) или добавьте пустое поле (пробел) в структуру после d.
Помогло! Ура!
Спасибо большое.

Появилась еще одна проблема.
Описание: при сортировке не хочет учитывать последнюю введенную строку. Покажу на рисунках:
Рис1: то что в файле (3 строки):
http://savepic.net/2742371.htm
Рис2: сортировка (сортирует две первые):
http://savepic.net/2734179.htm
Формирование и сортировка происходит в библиотеке bibl.cpp:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
void formir(FILE *f1,avto mas[],int n)
{f1=fopen("avto.dat","rb");
for(int k=0;k<n;k++)
{fread(&a,sizeof(a),1,f1);
mas[k]=a;}
fclose(f1);
}
 
void sort(avto mas[],int k)
{int i,j;
avto z;
for(i=0;i<=k;i++)
for(j=i+1;j<k;j++)
if((AnsiString)mas[i].god<(AnsiString)mas[j].god)
{(avto)z=(avto)mas[i];
(avto)mas[i]=(avto)mas[j];
(avto)mas[j]=(avto)z;}
}
А вывод сортировки в StrinGrid вот:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
void __fastcall TForm1::Button4Click(TObject *Sender)
{
setka(sg3);
int i,k=kol(f1);
avto *mas=new avto[k];
formir(f1,mas,k);
sort(mas,k);
for(i=0;i<=k;i++)
{
sg3->Cells[1][i+1]=AnsiString(mas[i].mark);
sg3->Cells[2][i+1]=AnsiString(mas[i].pr);
sg3->Cells[3][i+1]=AnsiString(mas[i].tip);
sg3->Cells[4][i+1]=AnsiString(mas[i].god);
sg3->Cells[5][i+1]=AnsiString(mas[i].d);
}
for(int j=1;j<=k;j++)
sg3->Cells[0][j]=IntToStr(j);
sg3->RowCount=k;
}
И две (в моем примере одна) функции в этом выводе участвует:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
void setka(TStringGrid *sg)
{sg->Cells[0][0]="№";
sg->Cells[1][0]="Марка авто";
sg->Cells[2][0]="Производитель";
sg->Cells[3][0]="Тип";
sg->Cells[4][0]="Год выпуска";
sg->Cells[5][0]="Дата регистрации";
}
 
void zapoln(TStringGrid *sg,int i)
{
sg->Cells[0][i]=IntToStr(i);
sg->Cells[1][i]=AnsiString(a.mark);
sg->Cells[2][i]=AnsiString(a.pr);
sg->Cells[3][i]=AnsiString(a.tip);
sg->Cells[4][i]=AnsiString(a.god);
sg->Cells[5][i]=AnsiString(a.d);
i++;
sg->RowCount=i;
}
Если, кто-нибудь знает, подскажите как исправить ошибку или в каком блоке она находится.
Спасибо
0
Практикантроп
4682 / 2601 / 497
Регистрация: 23.09.2011
Сообщений: 5,584
08.04.2012, 01:39 4
- глубоко не вникал, но в первом приближении вот здесь не правильно:
Цитата Сообщение от Pavel_n Посмотреть сообщение
sg->Cells[5][i]=AnsiString(a.d);
i++;
sg->RowCount=i;
... RowCount на единицу больше номера последней строки, а в Вашем примере Вы строку не добавляете, а "подтверждаете" существующее состояние. Попробуйте
C++
1
->RowCount=i+2;
1
1 / 1 / 2
Регистрация: 07.04.2012
Сообщений: 38
08.04.2012, 04:23  [ТС] 5
Цитата Сообщение от nick42 Посмотреть сообщение
- глубоко не вникал, но в первом приближении вот здесь не правильно:
... RowCount на единицу больше номера последней строки, а в Вашем примере Вы строку не добавляете, а "подтверждаете" существующее состояние. Попробуйте
C++
1
->RowCount=i+2;
Нет, не то. Это само заполнение и Я его именно в этом коде не использовал.
Но проблему нашел после Вашего сообщения
Вот где:
C++
1
2
3
4
5
6
7
sg3->Cells[4][i+1]=AnsiString(mas[i].god);
sg3->Cells[5][i+1]=AnsiString(mas[i].d);
}
for(int j=1;j<=k;j++)
sg3->Cells[0][j]=IntToStr(j);
sg3->RowCount=k+1;//Здесь поставил к+1
}
А в библиотеке:
C++
1
2
3
4
5
6
7
8
9
10
void sort(avto mas[],int k)
{int i,j;
avto z;
for(i=0;i<=k;i++)
for(j=i+1;j<k;j++)//Вот здесь убрал -1
if((AnsiString)mas[i].god<(AnsiString)mas[j].god)
{(avto)z=(avto)mas[i];
(avto)mas[i]=(avto)mas[j];
(avto)mas[j]=(avto)z;}
}
Огромное спасибо nick42 за помощь!
0
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
08.04.2012, 04:23

Ошибка при выводе файла на озвучку
Здравствуйте товарищи, есть проблема. Пытаюсь вывести файл на озвучку, в проге присутстует...

Ошибка при выводе строк из файла
Помогите пожалуйста разобраться в чем ошибка. Весь код писать не буду просто покажу как я вношу...

Ошибка при выводе файла записи
Задача состоит в том, что надо создать файл записи (музыка: исполнитель, название, год, жанр),...

Ошибка при чтении бинарного файла
почему у меня выводит два раза последнюю запись при чтении??(а файл записываю класс с 3...


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

Или воспользуйтесь поиском по форуму:
5
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2021, vBulletin Solutions, Inc.