2016-04-15 3 views
-1

В настоящее время я создаю пользовательский двоичный файл для огромного списка данных, который будет представлять некоторый угол движений в игре. Хотя я бегу в стену, пытаясь найти способ написать все данные, а затем прочесть их в огромный массив или вектор.Чтение списка объектов из двоичного файла

Вот как я построил мой FileFormat:

class TestFormat { 
    public: 
     float x; 
     float y; 
     float z; 
}; 

И тестовый код для записи и чтения:

int main() 
{ 
    TestFormat test_1, temp; 
    test_1.x = 4.6531; 
    test_1.y = 4.7213; 
    test_1.z = 6.1375; 

    // Write 
    ofstream ofs("test.bin", ios::binary); 
    ofs.write((char *)&test_1, sizeof(test_1)); 
    ofs.close(); 

    // Read 
    ifstream ifs("test.bin", ios::binary); 
    ifs.read((char *)&temp, sizeof(temp)); 
    ifs.close(); 

    cout << temp.x << endl; 
} 

Чтобы продлить этот код я могу просто написать дополнительные объекты в тот же файл , но я не уверен, как загрузить эти объекты в массив после этого.

+1

Вы только что написали, затем прочитали, * one *. Так сделайте это для более чем одного? – WhozCraig

+0

Подсказка: если объект занимает M последовательных байтов, то и массив из N таких объектов занимает N × M последовательных байтов. –

+0

Я понимаю, что вы говорите. Но как я могу использовать функцию 'read' для чтения нескольких объектов? – JavaCake

ответ

1

Вы могли бы сделать что-то вроде этого:

vector<TestFormat> test; 
    //.... 
    // Read 
    ifstream ifs("test.bin", ios::binary); 
    while(ifs.read((char *)&temp, sizeof(temp))){ 
    //tmp to array 
    test.push_back(TestFormat(temp)); 
    } 
    ifs.close(); 

Используя предложение Питера Barmettler в:

ifstream ifs("test.bin", ios::binary); 
ifs.seekg(0, std::ios::end); 
int fileSize = ifs.tellg(); 
ifs.seekg(0, std::ios::beg); 

vector<TestFormat> test(fileSize/sizeof(TestFormat)); 
ifs.read(reinterpret_cast<char*>(test.data()), fileSize); 
ifs.close(); 
+0

Это интересное решение. Хотя кажется, что он читает последнюю запись дважды? – JavaCake

+0

Да. Однако я не знаю, почему. Но вы можете либо игнорировать дубликат, либо использовать его в случае использования вектора. – Carafini

+0

Еще что-то я не понимаю с дубликатом на последнем объекте. – JavaCake

1

Например, если у вас есть на записи, вы можете сделать что-то вроде этого:

std::vector<TestFormat> temp(2); 

ifstream ifs("test.bin", ios::binary); 
ifs.read((char *)temp.data(), temp.size()*sizeof(TestFormat)); 
ifs.close(); 

cout << temp[1].x << endl; 
+0

У меня может быть x количество записей, поэтому ничего не могу определить. – JavaCake

+0

Тогда что-то вроде линий Адриано Карафини - это путь. Или вы поместите количество записей в заголовок вашего файла. –

Смежные вопросы