Подскажите, пожалуйста, мне необходимо создать библиотеку преобразования данных в определенный формат.
Откуда поступают данные, пока не известно, скорее всего это будет .csv. Моя задача записать эти данные в 3 файла, это будет бинарный файл, текстовый и xml. Пока у меня есть вот такой код, с помощью которого я создаю три файла.
Сейчас мне необходимо продумать интерфейс, изучив пространства интернета, в моем понятии интерфейс в с++, это тот же класс, который описывает методы, но не их реализацию. Поправьте меня, если ошибаюсь.
Вот на основании этого определения, я понимаю так, что в интерфейсе будут методы типа: чтение и запись файла. Не понимаю в том ли направлении думаю. С чего мне начать создание библиотеки? Объясните, для начинающего, пожалуйста!
// Struct.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include "xmlwriter.h"
using namespace std;
using namespace xmlw;
struct Station
{
string station_name;
string rec_dew;
string year;
};
struct InfaboutChanell
{
int chanellcount;
int analogChanell;
int discretChanell;
};
int main() {
//The first string
Station StationInfo;
StationInfo.station_name="Strathmore 251 kV";
StationInfo.rec_dew = "1";
StationInfo.year="2001";
ofstream file("D:\\Struct\\Struct\\ComtradeFormat\\fileConfiguration.cfg");
file<<StationInfo.station_name<<","<<StationInfo.rec_dew<<","<<StationInfo.year<<"\n";
//The information about count of channels
InfaboutChanell ChanellCount;
ChanellCount.chanellcount=14;
const int analogX =6;
ChanellCount.analogChanell = analogX;
const int discretX=8;
ChanellCount.discretChanell = discretX;
file<<ChanellCount.chanellcount<<","<<ChanellCount.analogChanell<<"A"<<","<<ChanellCount.discretChanell<<"D"<<"\n";
//The information about analog channels
struct InfAnalogChanel
{
int id;
string chanell_id;
string ph;
string ccmb;
string UU;
long float a;
double b;
double skew;
double min;
double max;
double Primery;
double Secondary;
string SP;
};
vector<InfAnalogChanel> s;
InfAnalogChanel a;
InfAnalogChanel b;
InfAnalogChanel c;
InfAnalogChanel d;
InfAnalogChanel e;
InfAnalogChanel f;
a.id=1;
a.chanell_id="ток ф А";
a.ph="";
a.ccmb="";
a.UU="A";
a.a=1.290489E-01;
a.b=0;
a.skew=0;
a.min=-32767;
a.max=32767;
a.Primery=3000.00000000;
a.Secondary=1.00000000;
a.SP="P";
b.id=2;
b.chanell_id="ток В";
b.ph="";
b.ccmb="";
b.UU="A";
b.a=5.139708E-02;
b.b=0;
b.skew=0;
b.min=-32767;
b.max=32767;
b.Primery=3000.00000000;
b.Secondary=1.00000000;
b.SP="P";
c.id=3;
c.chanell_id="ток фaза C";
c.ph="";
c.ccmb="";
c.UU="A";
c.a=7.745668E-02;
c.b=0;
c.skew=0;
c.min=-32767;
c.max=32767;
c.Primery=3000.00000000;
c.Secondary=1.00000000;
c.SP="P";
e.id=4;
e.chanell_id="расчит ноль";
e.ph="";
e.ccmb="";
e.UU="A";
e.a=4.860763E-02;
e.b=0;
e.skew=0;
e.min=-32767;
e.max=32767;
e.Primery=3000.00000000;
e.Secondary=1.00000000;
e.SP="P";
d.id=5;
d.chanell_id="напр В";
d.ph="";
d.ccmb="";
d.UU="V";
d.a=2.611292E+00;
d.b=0;
d.skew=0;
d.min=-32767;
d.max=32767;
d.Primery=60000.00000000;
d.Secondary=57.00000000;
d.SP="P";
f.id=6;
f.chanell_id="напр С";
f.ph="";
f.ccmb="";
f.UU="V";
f.a=2.621923E+00;
f.b=0;
f.skew=0;
f.min=-32767;
f.max=32767;
f.Primery=60000.00000000;
f.Secondary=57.00000000;
f.SP="P";
s.push_back(a);
s.push_back(b);
s.push_back(c);
s.push_back(e);
s.push_back(d);
s.push_back(f);
for(int i=0;i<s.size();++i)
file<<s[i].id<<","<<s[i].chanell_id<<","<<s[i].ph<<","<<s[i].ccmb<<","<<s[i].UU<<","<<s[i].a<<","<<s[i].b<<","<<s[i].skew<<
","<<s[i].min<<","<<s[i].max<<","<<s[i].Primery<<","<<s[i].Secondary<<","<<s[i].SP<<"\n";
//The information about discret chanells
struct InfDiscretChanel
{
int DN;
string ch_id;
string ph;
string ccmb;
int y;
};
vector<InfDiscretChanel> discret;
InfDiscretChanel first;
InfDiscretChanel sec;
InfDiscretChanel thre;
InfDiscretChanel four;
InfDiscretChanel five;
InfDiscretChanel six;
InfDiscretChanel seven;
InfDiscretChanel eight;
first.DN=1;
first.ch_id = "Раб МТЗ";
first.ph="";
first.ccmb="";
first.y=0;
sec.DN=2;
sec.ch_id = "3_3";
sec.ph="";
sec.ccmb="";
sec.y=0;
thre.DN=3;
thre.ch_id = "8_8";
thre.ph="";
thre.ccmb="";
thre.y=0;
four.DN=4;
four.ch_id = "8_100";
four.ph="";
four.ccmb="";
four.y=0;
five.DN=5;
five.ch_id = "3_8";
five.ph="";
five.ccmb="";
five.y=0;
six.DN=6;
six.ch_id = "3_8";
six.ph="";
six.ccmb="";
six.y=0;
seven.DN=7;
seven.ch_id = "29";
seven.ph="";
seven.ccmb="";
seven.y=0;
eight.DN=8;
eight.ch_id = "41";
eight.ph="";
eight.ccmb="";
eight.y=0;
discret.push_back(first);
discret.push_back(sec);
discret.push_back(thre);
discret.push_back(four);
discret.push_back(five);
discret.push_back(six);
discret.push_back(seven);
discret.push_back(eight);
for(int i=0;i<discret.size();++i)
file<<discret[i].DN<<","<<discret[i].ch_id<<","<<discret[i].ph<<","<<discret[i].ccmb<<","<<discret[i].y<<"\n";
//General information
struct GeneralInf
{
int ifone;
int nrates;
int samp;
int ensamp;
};
GeneralInf Information;
Information.ifone = 50;
Information.nrates = 1;
Information.samp = 1000;
Information.ensamp = 5107;
file << Information.ifone << "\n" << Information.nrates << "\n" << Information.samp << ","
<< Information.ensamp << "\n";
struct DateTime {
int dd;
int mm;
int yyyy;
int hh;
int min;
long float sec;
string type;
int nfile;
};
vector<DateTime> time;
DateTime samp;
DateTime endsamp;
samp.dd = 24;
samp.mm=10;
samp.yyyy=2017;
samp.hh=10;
samp.min=55;
samp.sec=14.546459;
endsamp.dd = 24;
endsamp.mm=10;
endsamp.yyyy=2017;
endsamp.hh=10;
endsamp.min =55;
endsamp.sec =14.647162;
time.push_back(samp);
time.push_back(endsamp);
for(int i=0;i<time.size();++i)
file<<time[i].dd<<"/"<<time[i].mm<<"/"<<time[i].yyyy<<","<<time[i].hh<<":"<<time[i].min<<":"<<time[i].sec<<"\n";
DateTime type;
type.type = "BINARY";
DateTime nnfile;
nnfile.nfile =1;
file<<type.type<< "\n"<< nnfile.nfile << "\n";
file.close();
// Create Binary file
fstream binary_file("fileConfiguration.dat",ios::out|ios::binary|ios::app);
if(!binary_file)
{
cout << "Cannot open file.\n";
return 1;
}
int i=0;
int n=0;
int timestamp =0;
for (i=0; i<=Information.ensamp; i++){
n = i+1;
binary_file.write((char *) &n, sizeof n);
timestamp = i*1000;
binary_file.write((char *) ×tamp, sizeof timestamp);
// Value of analog channels
short analogValue [analogX];
for(int i=0; i<analogX; i++)
analogValue[i] = rand() % 20000 - 10000;
binary_file.write((char *) &analogValue, sizeof analogValue);
unsigned __int16 m_bytesCount = 0;
m_bytesCount = discretX / 16;
if (discretX % 16){
m_bytesCount++;
}
int ChValue [discretX] = {1, 1, 1, 0, 0, 0, 0, 0};
for(int i = 0; i < discretX; ++i)
{
if(ChValue[i] == 1)
m_bytesCount |= 1 << i;
}
binary_file.write((char *) &m_bytesCount, sizeof m_bytesCount);
}
binary_file.close();
//Write XMLfile
ofstream filexml("fileHeader.xml");
XmlStream xml(filexml);
xml << prolog()<<"\n" // write XML file declaration
<<tag("general")<<"\n"
<< tag() << attr("general name") << "RecordId"<< attr("value") << "1"
<< endtag()<<"\n"
<< tag() << attr("general name") << "TrigDateTime"<< attr("value") << "24/10/2017,10:55:14.647"
<< endtag()<<"\n"
<< tag() << attr("general name") << "TrigChanell"<< attr("value") << "3_3"
<< endtag()<<"\n"
<< tag() << attr("general name") << "TrigWhileIEDinTestMode"<< attr("value") << "0"
<< endtag()<<"\n"
<< tag() << attr("general name") << "SequenceNumbe"<< attr("value") << "54"
<< endtag()<<"\n"
<< tag() << attr("general name") << "RecordingNumber"<< attr("value") << "108"
<< endtag()<<"\n
<< endtag("deep-tag"); // close all tags up to specified
return 0;
}
Если я правильно понял то можно сделать так(по простому):
Создаете примерно такой класс:
class CVS_API CvsReader
{
public:
CvsReader(const std::string fileName);
void readCvs();
void xmlWrite();
void textWrite();
void binWrite();
}
Создаете проект в VS с этим классом, в котором Configuration Type будет Dynamic Library(.dll). Далее создаете проект Application к которому подключаете свою библиотеку.
Думаю, интерфейс должен быть такой:
если контроль за конкретной операцией чтения-записи не нужен, то операции читать и вывести можно объединить в одну типа
если нужен внешний контроль за операциями чтения-записи (типа отлова ошибок), то
Основной рабочий класс должен сделать все проверки наличия входного файла и возможности вывода файла по заданному пути. Сделать запрос или ошибку если такой файл уже есть и тп (это уже детали реализации).
При задании типа выводимого файла нужно инициировать нужного потомка базового класса вывода (описано ниже).
Интерфейсные методы рабочего класса чтения и записи должны вызывать соответствующие методы созданного потомка базового класса.
Базовый абстрактный класс вывода и его потомки могут (должны?) быть internal для библиотеки и не видны снаружи.
Базовый абстрактный класс вывода должен реализовать метод чтения файла и иметь абстрактный метод для вывода файла.
Три потомка базового класса вывода - каждый реализует свой метод вывода.
Если типов источников данных может быть несколько, то в интерфейсе добавляется тип входного потока, Рабочий класс должен создавать соответствующий экземпляр базового класса для чтения данных. И в библиотеке добавляется еще одна структура наследования Базовый класс чтения - Потомки для каждого типа источника. При этом рабочий класс будет служить передаточным звеном для данных полученных из класса чтения в класс вывода.
Айфон мало держит заряд, разбираемся с проблемой вместе с AppLab
Перевод документов на английский язык: Важность и ключевые аспекты
Можно ли написать конструктор switch case со строковым типом переменных C++ ???
Работаю программистомМои программы успешно работают
Есть две формы: Form1 и Form2Они взаимодействую друг с другом, и при выполнении определенных действий во второй форме запускается цикл, идущий...