Russian Qt Forum
Ноябрь 23, 2024, 20:03 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: [1] 2   Вниз
  Печать  
Автор Тема: Обращение к данным по индексу  (Прочитано 10551 раз)
Pixel
Гость
« : Сентябрь 12, 2012, 14:02 »

Прочитал статью, про работу с данными в Qt и возник вопрос. Можно ли обращаться к конкретным данным, не читая при этом весь кусок файла, идущий перед нужными данными. Как я понял это работа с базами данных, но вразумительной статьи про них я не нашел. Подскажите, если не сложно, простенький способ обратиться к нужному куску данных или статейку про работе с БД для новичков.
Записан
mutineer
Гость
« Ответ #1 : Сентябрь 12, 2012, 14:05 »

Про какие данные ты говоришь? Где они лежат? Если ты про чтение из файла, то есть метод seek()
Записан
Pixel
Гость
« Ответ #2 : Сентябрь 12, 2012, 14:17 »

двоичные данные. Пример: есть структура с данными. Нужно сохранить много таких структур и записать в файл. Далее нужно будет обращаться к конкретной структуре, зная ее индекс или адрес или что угодно, что позволило бы обратиться к этой структуре, не считывая предыдущие.
Записан
mutineer
Гость
« Ответ #3 : Сентябрь 12, 2012, 14:23 »

seek тебе в помощь
Записан
Pixel
Гость
« Ответ #4 : Сентябрь 12, 2012, 14:29 »

Можно по подробней? чей это метод? QDataStream? QFile? Другой?
как его использовать? Нашел такой метод в QFile. Ну вот допустим я узнал, что по индексу 3 есть запись. Как мне теперь обратиться к структуре под номером 3?
« Последнее редактирование: Сентябрь 12, 2012, 14:36 от Pixel » Записан
Serr500
Гость
« Ответ #5 : Сентябрь 12, 2012, 14:34 »

Сначала QFile::seek. Если вернуло true, то QFile::read.

P.S. RTFM!
Записан
mutineer
Гость
« Ответ #6 : Сентябрь 12, 2012, 14:41 »

Можно по подробней? чей это метод? QDataStream? QFile? Другой?
как его использовать? Нашел такой метод в QFile. Ну вот допустим я узнал, что по индексу 3 есть запись. Как мне теперь обратиться к структуре под номером 3?

Методом seek пропустить первые две структуры (2 * размер структуры в байтах) и вычитать третью
Записан
Serr500
Гость
« Ответ #7 : Сентябрь 12, 2012, 14:48 »

mutineer
А щас он захреначит в файл class через QFile::write(this, sizeof(*this)) вместе с VMT и будет удивляться, почему оно падает.  Подмигивающий
« Последнее редактирование: Сентябрь 12, 2012, 15:29 от Serr500 » Записан
Pixel
Гость
« Ответ #8 : Сентябрь 12, 2012, 15:09 »

Честно говоря, я пока вообще не могу понять как и что можно записывать. Во всех примерах, что я читаю работают только с дата стримом, и ничего кроме этого:
struct str
{
    QString name;
};

...

QFile file("base.txt");
file.open(QIODevice::WriteOnly);
str dat;
dat.name="name";
QDataStream in(&file);
in<<dat.name;

у меня сделать не получается.
Метод Write я вообще не понял как работает.
Из документации:
write ( const char * data, qint64 maxSize )
второй аргумент это размер первого, а вот что в первом указывать я не понял. Структуру нельзя, данные структуры нельзя. Как что то туда записать?
Записан
Bepec
Гость
« Ответ #9 : Сентябрь 12, 2012, 15:30 »

Смотрим. Есть метод write ( const QByteArray & ) допустим.

Значит нам что надо сделать ? Правильно - запихать в QByteArray структуру, записать эту структуру. На обратной стороне (ты знаешь размер структуры) считать данные из QByteArray в том же порядке.

С QDataStream в принципе так же.

PS % на 70 уверен что это сработает. Ибо в последний раз сериализовал через Qt очень давно Веселый
Записан
Serr500
Гость
« Ответ #10 : Сентябрь 12, 2012, 15:33 »

С QDataStream в принципе так же.
Ему ещё позиционирование нужно и, скорее всего, нелинейное (вперёд-назад). А QDataStream позиционирование не поддерживает (только вперёд). Поэтому придётся брать QFile.
Записан
xokc
Птица говорун
*****
Offline Offline

Сообщений: 976



Просмотр профиля
« Ответ #11 : Сентябрь 12, 2012, 15:43 »

Давай сюда описание своей структуры. Запишем её в файл.
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #12 : Сентябрь 12, 2012, 15:55 »

А щас он захреначит в файл class через QFile::write(this, sizeof(*this)) вместе с VMT и будет удивляться, почему оно падает.  Подмигивающий
Так это неизбежный этап познания  Улыбающийся

Метод Write я вообще не понял как работает.
Из документации:
write ( const char * data, qint64 maxSize )
второй аргумент это размер первого, а вот что в первом указывать я не понял. Структуру нельзя, данные структуры нельзя. Как что то туда записать?
Этот метод предназначен для сохранения низкоуровневых данных, когда сохраненный на диске образ совпадает (байт в байт) с представлением объекта в памяти. Для чуть более сложного объекта (ну хоть QString) такое read/write не проходит, записанные данные не удается прочитать.

Я предлагаю такое решение: пишете через QDataStream, используя удобные операторы  <<. По ходу дела запоминаете позицию и размер записи напр так
Код
C++ (Qt)
... // открыли файл для записи
QDataStream strm(&theFile);
qint64 theDataStart = -1, theDataSize = -1;
...
theDataStart = strm.device()->pos();  // запомнили позицию первой записи
strm << theData;           // цивильно записали
theDataSize = strm.device()->pos() - theDataStart;  // запомнили размер записи на диске
 
Теперь читаем nth запись
Код
C++ (Qt)
void ReadRecNo( QDataStream & strm, int recNo, MyData & theData )
{
strm.device()->seek(theDataStart + theDataSize * recNo);
strm >> theData;          
}
 

Edit: ну разумеется это предполагает что все записи одного размера. Если это не так то надо создавать массив/контейнер theDataStart
« Последнее редактирование: Сентябрь 12, 2012, 16:06 от Igors » Записан
Pixel
Гость
« Ответ #13 : Сентябрь 12, 2012, 16:06 »

Всем спасибо! вроде как получилось. Вот:
    QFile file("base.txt");
    file.open(QIODevice::WriteOnly);

    str dat, dat2;
    dat.name="name";

    QByteArray arr;
    arr.resize(sizeof(dat));

    memmove(arr.data(), &dat, sizeof(dat));

    file.write(arr, sizeof(dat));

    file.close();
    arr.clear();

    file.open(QIODevice::ReadOnly);

    if (file.seek(0))
    {
        arr=file.read(sizeof(dat));
        memmove(&dat2, arr.data(), sizeof(dat));
    }

    qDebug()<<dat2.name;

Как то так. Выводит: "name". Посмотрите, такой способ корректен, ничего не напутал не намудрил?)
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #14 : Сентябрь 12, 2012, 16:11 »

Как то так. Выводит: "name". Посмотрите, такой способ корректен, ничего не напутал не намудрил?)
Mда, видимо в естественный процесс эволюции лучше не вмешиваться  Улыбающийся

Пользуйтесь тегом для обрамления кода
Записан
Страниц: [1] 2   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.123 секунд. Запросов: 23.