С Новым годом! Форум программистов, компьютерный форум, киберфорум
Наши страницы

С++ для начинающих

Войти
Регистрация
Восстановить пароль
 
 
Рейтинг: Рейтинг темы: голосов - 30, средняя оценка - 4.90
sadok
14 / 14 / 0
Регистрация: 26.01.2011
Сообщений: 64
#1

c++ работа с файлом - C++

26.01.2011, 03:42. Просмотров 3799. Ответов 23
Метки нет (Все метки)

Здраствуйте,в си знания - средненькие,мне предоставилась задача - нужно згенерировать файл для ипфильтра торрента,с сайта провайдера мне даётся только перечень адресов с которых трафик-бесплатный,тоесть мы имеем файлик - ip.txt в котором записаны адреса в формате -
22.55.105.30/20

Пишу консольку,вин 32,пустую.

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
#include "table.h"
void main()
{
    setlocale (LC_CTYPE, ".1251"); 
    setlocale (LC_MONETARY, ".1251"); 
    ifstream _in;
    _in.open("ip.txt",ios::_Nocreate);
    if(!_in)
        printf("Ненайден файл ip.txt");
    else 
    {
        cout<<"Файл найден,приступаем:";
        d();//дальше работаем с файлом
    }
    _in.close();
_getch();
}
 
void d()
{
    int num;//количество строк
    int col=0;//количество адресов занесенных в исходный масив
    int n=0;//колтчество знаков до значущой цыфры
    int ncol=3;//на сколько нужно добавить к индексу массива для сходства редактированого и нередактир.
    //равно трём т.к. первая точка встретится на 4-м индексе
    char buffer[20];    
    cout<<"\nоткрываем...";
    cout<<"\nВведите количество строк в файле";
    cin>>num;
    char** buf=new char*[num+1];//масив для наработки вид 0,00,0,000/00
    ifstream _in;
    _in.open("ip.txt");
    for(int i=0;!_in.eof();++i) //подсчет количества строк 
    {           
        _in.getline(buffer,21);
        cout<<'\n'<<buffer;//закоментировать
        buf[i]=buffer;
    }
    char **mas=new char* [num*2+3];//создание вертикального масива в первой ячейке 000,000,000,000 в последней 255,255,255,255
    for(int i=0;i<num;++i)
    {
        n=0;
        for(int x=0;x<20;++i)
        {
            switch(buf[i][x])
            {
            case '.':
                switch(n)//добавляем к ncol 4 потому,что следующая точка будет через 4-е индекса
                {
                case '3':buffer[ncol-3]=buf[i][x-3];buffer[ncol-2]=buf[i][x-2];buffer[ncol-1]=buf[i][x-1];ncol+=4;break;
                case '1':buffer[ncol-3]='0';buffer[ncol-2]='0';buffer[ncol-1]=buf[i][x-1];ncol+=4;break;
                case '2':buffer[ncol-3]='0';buffer[ncol-2]=buf[i][x-2];buffer[ncol-1]=buf[i][x-1];ncol+=4;break;
                }
                n=0;break;
            case '/':
                switch(n)//добавляем к ncol 4 потому,что следующая точка будет через 4-е индекса
                {
                case '3':buffer[ncol-3]=buf[i][x-3];buffer[ncol-2]=buf[i][x-2];buffer[ncol-1]=buf[i][x-1];ncol+=4;break;
                case '1':buffer[ncol-3]='0';buffer[ncol-2]='0';buffer[ncol-1]=buf[i][x-1];ncol+=4;break;
                case '2':buffer[ncol-3]='0';buffer[ncol-2]=buf[i][x-2];buffer[ncol-1]=buf[i][x-1];ncol+=4;break;
                }
                n=0;break;
            case '\0':
                switch(n)
                {
                case '3':buffer[ncol-3]=buf[i][x-3];buffer[ncol-2]=buf[i][x-2];buffer[ncol-1]=buf[i][x-1];ncol+=4;break;
                case '1':buffer[ncol-3]='0';buffer[ncol-2]='0';buffer[ncol-1]=buf[i][x-1];ncol+=4;break;
                case '2':buffer[ncol-3]='0';buffer[ncol-2]=buf[i][x-2];buffer[ncol-1]=buf[i][x-1];ncol+=4;break;
                }
                n=0;break;
            default:++n; break;
            }
            
        }
 
    }
    
    
    
 }

ошибку выбивает в свитче,но если использую иф- то ошибка тоже вылетает,насколько я понял у меня незаполняется массив?Код писал с нуля уже 6-й раз,каждый раз пробуя по разному считывать,т.к. в си множество способов.

ошибка - Unhandled exception at 0x00a11946 in ip.exe: 0xC0000005: Access violation reading location 0xcdcdcdcd.
предлагает продолжить или прервать

п.с. пользуюсь Visual Studio 2008
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
26.01.2011, 03:42
Здравствуйте! Я подобрал для вас темы с ответами на вопрос c++ работа с файлом (C++):

Работа с файлом в С++ - C++
Всем привет! Я никогда не работал с С++, но возникла необходимость чтения-записи в файл на С++. А если еще точнее Embedded C++. Не...

Работа с файлом - C++
char *FileName =&quot;123.txt&quot;; int h=fileno(fopen(FileName,&quot;r+&quot;)); FileName=&quot;\0&quot;; Как мне теперь используя только h работать с файлом?...

Работа с файлом - C++
#include &lt;iostream&gt; #include &lt;string&gt; using namespace std; struct STUDENT // структура STUDENT { string name; ...

Работа с файлом - C++
Написать программу, которая считывает текст из файла и выводит на экран только цитаты, то есть предложения, заключенные в кавычки.

Работа с файлом - C++
Пожалуйста, помогите решить задачку.. Написать на чистом C (без использования C++) консольную программу, которая: - Считывает с диска...

Работа с файлом - C++
в общем есть некая решенная задача которая имеет классы и методы(ввода и вывода) для них, нужно ювелирно переделать методы так чтоб они...

23
sadok
14 / 14 / 0
Регистрация: 26.01.2011
Сообщений: 64
31.01.2011, 00:59  [ТС] #16
вот,но ето только насчёт последних чисел,а насчёт количества нужно компилировать,там если до знака / меньше определённого количества,то результаты вывода последней строки-меняются. по чему-то влияние на вывод идёт по последней строчке
0
Миниатюры
c++ работа с файлом  
sadok
14 / 14 / 0
Регистрация: 26.01.2011
Сообщений: 64
31.01.2011, 01:02  [ТС] #17
вот несколько примеров
0
Миниатюры
c++ работа с файлом   c++ работа с файлом  
sadok
14 / 14 / 0
Регистрация: 26.01.2011
Сообщений: 64
31.01.2011, 01:03  [ТС] #18
причём на листе бумаги всё идёт идеально((( тоесть расписываю каждый проход цикла.
Может проблема в подсчёте '\n' в свитче, пробовал и '\0' -только его вообще невидет,тоесть выбивает ошибку - num<4,тоесть равен 3-м
0
accept
4828 / 3249 / 165
Регистрация: 10.12.2008
Сообщений: 10,569
31.01.2011, 06:41 #19
Цитата Сообщение от sadok
стринг вышел из диапазона
C++
1
for(int x=0;x<=mas[i].length();x++)
x <

C++
1
case '\n':
это когда такой случай наступит ?
getline() не сохраняет их

C++
1
case '/':
подразумевает, что там три символа после слеша

с числами лучше работать, когда они являются числами
то есть эти числа считываются прямо в int переменные, чтобы потом можно было их сравнивать
есть stringstream - такая штука, с помощью которой можно строку превратить в поток и считывать из неё в переменные
C++
1
2
3
4
5
6
7
8
    int o[4], m;
    char sep[4];
 
    ss >> o[0] >> sep[0]
       >> o[1] >> sep[1]
       >> o[2] >> sep[2]
       >> o[3] >> sep[3]
       >> m;
0
sadok
14 / 14 / 0
Регистрация: 26.01.2011
Сообщений: 64
31.01.2011, 17:26  [ТС] #20
непонял,можно пример,что-то неврубаюсь - потом стиргстим только сейчас буду учить =))) я вектортолько позавчера выучил=))
0
accept
4828 / 3249 / 165
Регистрация: 10.12.2008
Сообщений: 10,569
01.02.2011, 06:26 #21
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
#include <iostream>
#include <string>
#include <sstream>
 
using namespace std;
 
int main(void)
{
    string s = "1.2.3.4/11";
    stringstream ss;
    
    ss.str(s);
    
    int o[4], m;
    char sep[4];
 
    ss >> o[0] >> sep[0]
       >> o[1] >> sep[1]
       >> o[2] >> sep[2]
       >> o[3] >> sep[3]
       >> m;
 
    cout << "ip: ";
    for (int i = 0; i < 4; i++)
        cout << o[i] << (i + 1 < 4 ? "." : "\n");
    cout << "mask: " << m << endl;
    
    cout << "seps: ";
    for (int i = 0; i < 4; i++)
        cout << sep[i] << (i + 1 < 4 ? " " : "\n");
    
    return 0;
}
Код
[guest@localhost tests]$ .iso++ t.cpp -o t
[guest@localhost tests]$ ./t
ip: 1.2.3.4
mask: 11
seps: . . . /
[guest@localhost tests]$
то есть ты сначала читаешь строку через getline(), потом подаёшь её в is_ipmask(), и если там всё ровно, разделяешь её через stringstream
1
sadok
14 / 14 / 0
Регистрация: 26.01.2011
Сообщений: 64
24.09.2011, 22:55  [ТС] #22
Прошло время и я опять взялся за выполнение етого задания,я немного поднатаскался написал вот -

main.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
34
35
36
37
38
39
40
41
42
43
44
45
#include "yy.h"
 
 
 
string IntToStr(int x)// преобразовывает int в string
{
        char buf[4];
        sprintf(buf,"%d",x);
        return buf;
}
 
 
void main()
{
    setlocale(LC_ALL,"");
    string s;
    cout<<"Ведите имя файла для чтения:  ";
    getline(cin,s);// считываем имя файла
    s+=".txt";
    ifstream ip_in(s.c_str());
    ip_adress ip_base(ip_in);// создаём наш обьект класа ip_adress
    if(!ip_in) cout<<endl<<"ошибка файл не найден";
    while(!ip_in.eof())
    {
        ip_base.read(ip_in);
        ip_base.write(lin1);
        ip_base.write(lin2);
    }
    ip_base.write("255.255.255.255");//вводим в масив адресов,последний ,максимальный адресс
 
    /*cout<<endl<<"файл-"<<endl;
    for(int i=0;i<ip_base.size();++i) // проверка состояние данных в потоке ip_base
        cout<<ip_base.see(i)<<endl;*/
    cout<<"Ведите имя файла для вывода:  ";
    getline(cin,s);
    s+=".txt";
    ofstream ip_out(s.c_str());
    for(int i=0;i<ip_base.size();i+=2)
    {
        //if((i/2)==(double)(i/2)) cout<<"(i/2)"<<(i/2)<<"(int)(i/2)"<<(double)(i/2)<<endl;
        ip_out<<ip_base.see(i)<<'-'<<ip_base.see(i+1)<<",000,NonUAIX"<<endl;
    }
    cout<<"Выполнено успешно";
    _getch();
}
файл yy.h
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
83
84
85
86
87
88
89
90
91
92
93
#pragma once
#include "iostream"
#include "conio.h"
#include "string"
#include "fstream"
#include<vector>
using namespace std;
 
 
string IntToStr(int x);
 
string lin1;//x   (x/_)
string lin2;//x   (_/x)
 
 
class ip_adress {
public:
    ip_adress(istream& is):sourse(is)  {mas.push_back("0.0.0.0");}
    //конструктор изначально создаёт начальный адресс 0.0.0.0
    void read(istream& is);
    //функция считывает  из указаного потока _is_ построчно значения и заполняет две глабальные переменные _lin1_ и _lin2_ - каждый раз обнуляя их
    void write(string s);
    //функция добавляет строку _s_ в елемент класа _mas_
    int size();
    //возвращает количество елементов в векторе _mas_
    string see(int i);
    //возвращает строку из вектора _mas_ с индексом _i_
private:
    istream& sourse;//источник информации
    vector<string> mas;//вектор со строками, формат строки - ХХХ.ХХХ.ХХХ.ХХХ
};
 
 
void ip_adress::read(istream & is)//ввод в класс значение из потока файла S
{
    //функция считывает строку формата  ХХХ.ХХХ.ХХХ.ХХХ/ННН
    //преобразовывает в две строки - ХХХ.ХХХ.ХХХ.ХХХ и ХХХ.ХХХ.ХХХ.ННН
    //потом записывает их в глобальные переменные lin1 и lin2
    string line;//xxx.
    lin1="";//x   (x/_)
    lin2="";//x   (_/x)
    int mnt1,mnt2;//переменные для сохранения двух значений - m[0].[mnt1].[mnt2].m[4]
    char a[4];//в масив символов будет помещатся-точки и слеш  ( .   /   )
    int m[5];//будет хранится 5-ть значений ХХХ (ХХХ.ХХХ.ХХХ.ХХХ/ХХХ)
    for(int i=0;i<4;++i)
    {
        is>>m[i]>>a[i];
        cout<<m[i]<<a[i];
    }
    is>>m[4];
    cout<<m[4]<<endl;
 
    mnt2=m[2];//копируем значения - m[0].[mnt1].[mnt2].m[4]
    mnt1=m[1];
 
    m[4]+=1;
 
    if(m[3]<1)// в етом условии и else - мы изменяем на единицу начальный адрес,тоесть приводим к адресу на 1-цу меньше чем считано с файла
        {
            if(m[2]<1)
            {   
                if(m[1]<1){}
                else {m[1]-=1;m[2]=255;m[3]=255;}
            }
            else {m[2]-=1;m[3]=255;}
        }    
    else m[3]-=1;
 
        line+=IntToStr(m[0]); // создаём начальную,одинаковую для обоих адресов,точку - ХХХ.  
        line+='.';
 
    lin1=line+IntToStr(m[1])+'.'+IntToStr(m[2])+'.'+IntToStr(m[3]);//создаём строки формата ХХХ.ХХХ.ХХХ.ХХХ
    lin2=line+IntToStr(mnt1)+'.'+IntToStr(mnt2)+'.'+IntToStr(m[4]);
 
    cout<<endl<<lin1<<endl;//проверяем созданые строки с данными - ХХХ.ХХХ.ХХХ.ХХХ
    cout<<lin2<<endl;
    _getch();
}
 
void ip_adress::write(string s)
{
    mas.push_back(s);
}
 
int ip_adress::size()
{
    return mas.size();
}
 
string ip_adress::see(int i)
{
    return mas[i];
}
вполне рабочая программа,но с хоть и не единственными недоработками,но плохо работает функция -
C++
1
2
3
4
5
6
string IntToStr(int x)// преобразовывает int в string
{
        char buf[4];
        sprintf(buf,"%d",x);
                return buf;
}
а собственно,функция должна возвращать строку вида - 001 и т.д.
к примеру x=5 ,то программа должна вернуть строку = 005
если х=14,то вернуть строку = 014

тоесть мне нужно организовать функцию перевода int в string ,string формата (XXX),тоесть 3-х значную строку


из-за етой функции,у меня программа в файл записывает -
источник файл - 1.1.1.2/10
файл выхода-
0.0.0.0-1.1.1.1,000,nonuaix
1.1.1.11-255.255.255.255,000,nonuaix

а цель программы в файле вывода вывести -
000.000.000.000-001.001.001.001,000,nonuaix
001.001.001.011-255.255.255.255,000,nonuaix
0
accept
4828 / 3249 / 165
Регистрация: 10.12.2008
Сообщений: 10,569
25.09.2011, 06:38 #23
Цитата Сообщение от sadok
а собственно,функция должна возвращать строку вида - 001 и т.д.
к примеру x=5 ,то программа должна вернуть строку = 005
если х=14,то вернуть строку = 014
C++
1
2
3
4
5
6
7
8
9
10
11
#include <string>
#include <cstdio>
 
// преобразовывает int в string
string IntToStr(int x)
{
    char buf[4];
 
    sprintf(buf, "%03d", x);
    return buf;
}
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
#include <string>
#include <sstream>
 
// преобразовывает int в string
string IntToStr(int x)
{
    ostringstream oss;
    
    //x %= 1000;
    oss.width(3);
    oss.fill('0');
    oss << x;
    return oss.str();
}
1
sadok
14 / 14 / 0
Регистрация: 26.01.2011
Сообщений: 64
25.09.2011, 19:51  [ТС] #24
всё работает!
итак программа принимает имя файла(имя.txt),формат файла -
HTML5
1
2
1.1.2.4/5
3.6.5.4/8
тоесть принимает адреса входящие в зону бесплатного трафика и инвентирует ети адреса в обратное список адресов с которых не будет производится скачивание или отдача трафика.
Тоесть преобразует в понятный для торента синтаксис -
HTML5
1
2
3
000.000.000.000-001.001.002.003,000,nondownload
001.001.002.005-003.006.005.003,000,nondownload
003.006.005.009-255.255.255.255,000,nondownload
вот окончательный код написан на один пост выше,изменение только в файле main.cpp-
main.cpp
C++
1
2
3
4
5
6
7
8
9
10
11
#include <sstream>
string IntToStr(int x)// преобразовывает int в string
{
    ostringstream oss;
    
    //x %= 1000;
    oss.width(3);
    oss.fill('0');
    oss << x;
    return oss.str();
}
0
25.09.2011, 19:51
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
25.09.2011, 19:51
Привет! Вот еще темы с ответами:

Работа с файлом - C++
Добрый вечер. Нужно подсчитать количество точек, попадающих в круг радиуса 4 с центром в начале координат. На паскале такую прогу уже делал...

C++. Работа с файлом - C++
Всем привет!!Написала код!!Нужно чтобы текст из файла переводился в Морзе!По отдельности они работают!А как соединить не знаю(((Помогите...

работа с файлом) - C++
Помогите пжлст написать прогу.Задание: Найти среднее количество знаков препинания в абзаце.Текст считывать с файла. Добавлено через...

работа с файлом - C++
объясните, пожалуйста, что тут происходит. особенно строчку, где ofs.write(reinterpret_cast&lt;char const*&gt;(arr), n * sizeof(*arr)); ...


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

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

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