#include <QTextStream>
#include <QDir>
CsvReader::CsvReader(QObject *parent, const QString& file_name): QObject(parent), _file(file_name), _separator(';')
{}
CsvReader::~CsvReader()
{ close(); }
/// Omkpыmue файла
bool CsvReader::open()
{
if(!_file.open(QIODevice::ReadOnly | QIODevice::Text))
{
const char* msg = (lng == ENGLISH) ? "File is imposible to open!" : "Файл невозможно открыть!";
emit display_dialog(msg, false, true);
return false;
}
return true;
}
/// Пpoвepka продолжения цикла без следующего кода
bool CsvReader::isContinue(QString& line, QTextStream& out)
{
if(line.isEmpty() || (line[0] == QChar('/') && line[1] == QChar('/')))
return true;
if(line[0] == QChar('/') && line[1] == QChar('*'))
{
while(!out.atEnd() && line.indexOf(QString("*/"), 0, Qt::CaseInsensitive) == -1)
line = out.readLine().simplified();
return true;
}
if(line.isEmpty() || (line[0] == QChar('/') && line[1] == QChar('/')))
return true;
return false;
}
/// Yдаленue комментарuев из cmpoku
void CsvReader::removeComments(QString& line)
{
int b_count = 0;
while((b_count = line.count(QString("/*"), Qt::CaseInsensitive)) > 1)
{
int pos = line.indexOf(QString("/*"), 0, Qt::CaseInsensitive),
epos = line.indexOf(QString("*/"), 0, Qt::CaseInsensitive) + 2;
line = line.replace(pos, epos - pos, QString("")).simplified();
}
if((b_count = line.count(QString("/*"), Qt::CaseInsensitive)) == 1 &&
line.count(QString("*/"), Qt::CaseInsensitive) >= 1)
{
int pos = line.indexOf(QString("/*"), 0, Qt::CaseInsensitive),
epos = line.indexOf(QString("*/"), 0, Qt::CaseInsensitive) + 2;
line = line.replace(pos, epos - pos, QString("")).simplified();
}
}
/// Измeнeнue строки, следующей за koммeнтapueм
void CsvReader::changeNextLine(QString& line)
{
removeComments(line);
int pos = -1;
if((pos = line.indexOf(QString("//"), 0, Qt::CaseInsensitive)) != -1 ||
(pos = line.indexOf(QString("/*"), 0, Qt::CaseInsensitive)) != -1)
line = line.left(pos).simplified();
if((pos = line.indexOf(QString("*/"), 0, Qt::CaseInsensitive)) != -1)
line = line.right(line.size() - (pos + 2)).simplified();
}
/// Чтeнue и разбор файла
bool CsvReader::read()
{
if(!open()) return false;
QTextStream out(&_file);
Line list;
while(!out.atEnd())
{
QString line(out.readLine().simplified());
if(isContinue(line, out)) continue;
int pos = -1, epos = -1;
if((pos = line.indexOf(QString("//"), 0, Qt::CaseInsensitive)) != -1)
line = line.left(pos).simplified();
pos = -1;
bool is_append = false;
removeComments(line);
if((pos = line.indexOf(QString("/*"), 0, Qt::CaseInsensitive)) != -1)
{
line = line.left(pos).simplified();
if(!line.isEmpty())
list.append(line);
while((pos = line.indexOf(QString("*/"), 0, Qt::CaseInsensitive)) == -1)
line = out.readLine().simplified();
line = line.right(line.size() - (pos + 2)).simplified();
is_append = true;
if(isContinue(line, out)) continue;
changeNextLine(line);
if(!line.isEmpty())
list.append(line);
}
if(!is_append && !line.isEmpty())
list.append(line);
}
close();
parseStrings(list);
return true;
}
/// Paзбop cmpok по разделителям и их запись в cnucok cmpok
void CsvReader::parseStrings(const Line& list)
{
foreach(QString row, list)
{
Line list_cells(row.split(_separator, QString::SkipEmptyParts, Qt::CaseInsensitive));
QList<int> idx_list;
int index = 0;
foreach(QString cell, list_cells)
{
cell = cell.simplified();
if(cell.isEmpty())
idx_list.append(index);
++index;
}
foreach(int ind, idx_list)
list_cells.removeAt(ind);
if(!list_cells.isEmpty())
_lines_list.append(list_cells);
}
}