PDA

Просмотр полной версии : Программа для универа


Meister
23.12.2005, 01:32
Я прошу помочь решить одну проблему, но проблема не типа "Решите мне задачу", просто до меня не дойдет как сделать следующее:
"Дан текстовый файл с неизвестным количеством вещественных чисел Написать функцию для определения есть ли среди них число у которого равны сумма цифр целой и дробной части"
У меня получилось сделать так, чтобы прграмма отвечала на каждое число, равны ли его сумма дробной и целой части:

#include <conio.h>
#include <fstream.h>
#include <iostream.h>
#include <stdlib.h>
#include <stdio.h>

void main()
{
char fni[256];
const N = 100;
cout<<"enter filename of input file\n";
cin>>fni;
double* pn=new double[N];
fstream fi;
fstream fo;
fi.open(fni,ios::in);
for(int i=0;(!fi.eof())&&(i<N);i++)
{
fi>>pn[i];
char a[20],b[20];
sprintf(b,"%f",pn[i]-((int)pn[i]));
char* tb=b;
tb+=2;
while(*tb=='0') tb++;
sprintf(a,"%d",(int)pn[i]);
int ia=0,ib=0;
char tmp[2];
for(int j=0;j<20;j++)
{
tmp[0]=a[j]; tmp[1]='\0';
ia+=atoi(tmp);
}
for(int j=0;tb[j]!='\0';j++)
{
tmp[0]=tb[j]; tmp[1]='\0';
ib+=atoi(tmp);
}
if(ia==ib) fo<<printf("DA - EST");
else printf("NET - NETU");
}
delete [] pn;
fi.close();
fo.close();
getch();
}

Потом, я парился парился и допарился, что выводит ответ один, но лишь для первого числа в файле:

#include <conio.h>
#include <fstream.h>
#include <iostream.h>
#include <stdlib.h>
#include <stdio.h>

int main()
{
char fni[256];
const N=100;
cout<<"enter filename of input file\n";
cin>>fni;
double* pn=new double[N];
fstream fi;
fstream fo;
fi.open(fni,ios::in);
for(int i=0;(!fi.eof())&&(i<N);i++)
{
fi>>pn[i];
char a[20],b[20];
sprintf(b,"%f",pn[i]-((int)pn[i]));
char* tb=b;
tb+=2;
while(*tb=='0') tb++;
sprintf(a,"%d",(int)pn[i]);
int ia=0,ib=0;
char tmp[2];
for(int j=0;j<20;j++)
{
tmp[0]=a[j]; tmp[1]='\0';
ia+=atoi(tmp);
}
for(int j=0;tb[j]!='\0';j++)
{
tmp[0]=tb[j]; tmp[1]='\0';
ib+=atoi(tmp);
}
if(ia==ib) printf("DA - EST");
else printf("NET - NETU");
getch();
return 0;
}}

А мне нужно, чтобы программа не по первому числу отвечала, а анализируя все. Никто не возьмется меня поправить?

Mymik
23.12.2005, 13:28
Вобщем вот мой вариант :-)... я потоки в сишниках не люблю... потому сделал немного по другому, только единственная проблема... у меня тут нет ни сишника, ни хелпа, вобщем нихера нет :-) так что за работоспособность не отвечаю :-) точнее я только сомневаюсь в условиях где я проверял на ansii-код сиволы... посмотри, если не будет работать :-). Там надо сравнить какой код у считываемого символа. Если он входит в диапозон где хранятся цифры, то мы выполняем действи... а если нет, то пропускаем...
Вобщем если будут вопросы пиши :-) будем дальше программить без компилятора :-D
#include <stdio.h>
#include <conio.h>

void main(void){
FILE *f;
char fileName[20]; // адрес к файлу
printf("Введите имя файла -->");
scanf("%s", fileName); // считываем пусть к нему
f = fopen(name, "r"); // берем хандл на файл
char number;
int left = 0;
int right = 0;
int comma = -1;
int floatIsHere = 0;
while(!feof){ // цикл пока не конец файла

fscanf(f, "%c", number);
if(number == 32){ //32 это ansii-код пробела
if(left == right)floatIsHere++; //если лева и правая часть равна, то прибавляем
left = 0; // обнуляем сумму цифр левее запятой
right = 0; // обнуляем сумму цифр правее запятой
comma = -1; // готовимся к обработки следующего числа, т.е. к обработке цифры левее запятой
continue;
} // end if
if(number == ','){
comma = 1; // готовимся к обработке цифр правее запятой
continue; // пропускаем все оставшиеся действие цикла и становимся на следующий шаг
} // end if
if((number => 49) && (number =< 59) && (comma == -1))//я точно не помню ansii-кода символом 1-0 посмотри их
left += atoi(number);
if((number => 49) && (number =< 59) && (comma == 1))
right += atoi(number);
} // ned while
if(floatIsHere >= 1)printf("В файле есть бла-бла-бла и их количесво %d", floatIsHere);
getch();
} // programm end

qBiN
23.12.2005, 17:35
printf("Введите имя файла -->");
scanf("%s", fileName); // считываем пусть к нему
f = fopen(name, "r"); // берем хандл на файлЧувак апкурился наверное записывает имя файла в fileName а использует переменную name которая даж не объявляется.
Астальное лень смотреть.

Dronga
23.12.2005, 19:02
Чувак апкурился наверное записывает имя файла в fileName а использует переменную name которая даж не объявляется.
Астальное лень смотреть.зря ты так отзываешься, без компилятора реально ещё не так напортачить, да и чел предупредил что никаких гарантий, полная импровизация, так что всё нормуль для кода написанного на лету :)

Meister, жаль ты в Си делаешь, в паскале помог бы.

Meister
23.12.2005, 19:19
общем если будут вопросы пиши :-)
Да уж, вопросы есть, не знаю как идея, но в целом там много ошибок, которые не поддаются моему исправлению
использует переменную name которая даж не объявляется.
Именно об этом комилятор сообщает первым делом.
Dronga, а ты аватару сменил?

qBiN
23.12.2005, 20:27
полная импровизация, так что всё нормуль для кода написанного на летуну уж простите,но переменные которые используешь надо помнить...
fscanf(f, "%c", number);Не есть гуд. лучше просто брать символ (fputc) а то я не помню фсанф прокручивает файл или нет =) Да и вопще хорошо(и быстрее) будет работать с fputc, функции форматированного ввода медленее...

nerezus
23.12.2005, 21:02
Ну про явные ошибки типа void main никто не сказал? =)

Mymik
24.12.2005, 20:46
Господа :-) а может все таки напишим челу программу... ну нашли ошибки, так исправте :-) я ж сказал, что я писал без какого-либо компилятора и хелпа... все писалось из памяти :-(... и в блакноте :-)

А что за ошибка void main(void) ??? мне очень интересно... Чтобы на это матюкались слышу впервые... Расскажи, я реально не знаю

nerezus
24.12.2005, 20:55
А что за ошибка void main(void) ??? мне очень интересно... main может быть только типа int
Иначе не компилирует. (только древние компиляторы проглатывают войд)

Deem3n®
25.12.2005, 00:08
Mymik этот вариант написанный в блокноте весьма неплохой )) (кстати от меня +) я его переделал в полне работоспособный:
#include <stdio.h>
#include <conio.h>

int main()
{
FILE *f;
// нафига вводить имя файла? сразу открываем input.txt
if ((f = fopen("input.txt", "rt"))== NULL)
{
fprintf(stderr, "Cannot open input file.\n");
return 1;
}

clrscr(); // очищаем экран
char ch; // текущий считываемый символ
int left = 0; // сумма цифр левее запятой
int right = 0; // сумма цифр правее запятой
int comma = 0;

while (!feof(f))
{
fscanf(f, "%c", &ch); // будем читать посимвольно

if (ch=='.')
{
comma = 1; // готовимся к обработке цифр правее запятой
printf("%c", ch); // выводим текущий символ
continue; // пропускаем все оставшиеся действие цикла и становимся на следующий шаг
}

if ((ch>='0') && (ch<='9') && (comma == 0))
left += int (ch) - 48; // int (ch) - ASCII код символа, int('0')=48 ... int('9')=57
if ((ch>='0') && (ch<='9') && comma)
right += int (ch) - 48;

if (ch == '\n') // если текущий символ - конец строки
{
if (left==right) printf("\t\tYES\n");
else printf("\t\tNO\n");
left=right=comma=0;
continue; // пропускаем все оставшиеся действие цикла и становимся на следующий шаг
}
printf("%c", ch); // выводим текущий символ
}
fclose(f);
return 0;
}
Тестил, работает 100%
Input.txt
23233.232332
1111.1111
32.545435
2222.11114
5435.5435322
2222.44
4345.654654
Result:

23233.232332 NO
1111.1111 YES
32.545435 NO
2222.11114 YES
5435.5435322 NO
2222.44 YES
4345.654654 NO

Meister
25.12.2005, 15:01
Господа, я наверно мало внимания уделил постановке задачи, когда писал пост, но нужно просто ...Написать функцию для определения есть ли среди них число у которого равны сумма цифр целой и дробной части" И я говорю именно, что у меня получилось только по каждому числу, а мне надо в общем, есль ли ли такое число в файле, или нет. И на экран вывести Да или Нет. Димеру и Мумику по плюсу за желание мне помочь.

Да кстати, Димер, щас проверил твою прогу, просто черныый экран вылетает и сворачивается обратно, прога завершается. Мы делаем в такой среде: File >> New >> Other >> Console Wizard >> Галочки на C++ только оставить.

Deem3n®
25.12.2005, 17:02
а мне надо в общем, есль ли ли такое число в файле, или нет
ну переделать не проблема:
#include <stdio.h>
#include <conio.h>

// Функция возвращает:
// 1 - если в файле есть число у которого равны сумма цифр целой и дробной части
// 0 - если этого числа нет
// -1 - ошибка I/O
int exists(const char* file_name)
{
FILE *f;
char ch; // текущий считываемый символ
int left = 0; // сумма цифр левее запятой
int right = 0; // сумма цифр правее запятой
int comma = 0;

if ((f = fopen(file_name, "rt"))== NULL)
{
fprintf(stderr, "Cannot open input file.\n");
return -1;
}

while (!feof(f))
{
fscanf(f, "%c", &ch); // будем читать посимвольно

if (ch=='.')
{
comma = 1; // готовимся к обработке цифр правее запятой
continue; // пропускаем все оставшиеся действие цикла и становимся на следующий шаг
}

if ((ch>='0') && (ch<='9') && (comma == 0))
left += int (ch) - 48; // int (ch) - ASCII код символа, int('0')=48 ... int('9')=57
if ((ch>='0') && (ch<='9') && comma)
right += int (ch) - 48;

if (ch == '\n') // если текущий символ - конец строки
{
if (left==right) return 1;
left=right=comma=0;
}
}
fclose(f);
return 0;
}


int main()
{
char file_name[255];
printf("Enter filename:");
scanf("%s", &file_name);
switch (exists(file_name))
{
case 1: printf("YES"); break;
case 0: printf("NO"); break;
default: printf("I/O Error"); break;
}
getch();
return 0;
}
компилится и работает без проблем в TC++ и Visual Studio

Meister
25.12.2005, 17:38
Как-то он по разному отвечает, например на числа
11.12
23.34
12.12

отвечает
NO
Это же не может быть связано с тем, что я использую C++ Builder 6?

Deem3n®
25.12.2005, 22:38
Как-то он по разному отвечает, например на числа
11.12
23.34
12.12

отвечает
NO
Это же не может быть связано с тем, что я использую C++ Builder 6?
после последнего номера в файле надо нажать <Enter>
http://users.cjb.net/spydeem3n/gliuk.jpg

Meister
26.12.2005, 01:02
Deem3n® А почему так получается, что если ентер в конце есть, то всегда Yes?