Модераторы: xvr

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> нехватка оперативной памяти ? 
:(
    Опции темы
Remiznik
Дата 3.8.2009, 22:35 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 379
Регистрация: 30.4.2005

Репутация: нет
Всего: 1



просто я использую эти данные для дальнейшей обработки ....можно конечно напрямую данные брать из файла на диске но это при большом количестве обращений к файлу очень влияет на время работы.
PM MAIL   Вверх
andrew_121
Дата 3.8.2009, 22:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Кодофей
****


Профиль
Группа: Завсегдатай
Сообщений: 3448
Регистрация: 3.1.2008

Репутация: 3
Всего: 33



Remiznik, Ты не понял.

Цитата(andrew_121 @  3.8.2009,  22:27 Найти цитируемый пост)
Какие именно операции ты выполняешь с этим вектором? 

Т.е. Какие методы вектора, содержащего данные из этого файла, тебе нужны?

Пример:
Код

struct mystruct {
    int param1;
    int param2;
};


template<typename T> class MyVector {
public:
    MyVector(const std::string& filename) {
        ...
        uint filesize = ...;
        int fd = open(filename, ...);
        
        _ptr = mmap(..., fd, ...); /* <<<<<<<<<<<<<<<<<<<<<<<< */
        
        _count = filesize / sizeof(T);
    }
    const T& operator[] (int idx) const {
        if ( idx <= _count ) {
            return *(const T*)_ptr+idx*sizeof(T);
        }
        return T(); /* что-то типа этого или исключение*/
    }
protected:
    uint _count;
    char* _ptr;
};

int main(int argc, const char **argv) {
    MyVector<mystruct> vec("./file.dat");
    return 0;
}


Вот. Реализуй необходимые тебе методы.

Добавлено @ 22:52
Я показал пример реализации вектора с перегруженным оператором индексирования.

Это сообщение отредактировал(а) andrew_121 - 4.8.2009, 11:15


--------------------
Удалил аккаунт. Прощайте!
PM MAIL   Вверх
Remiznik
Дата 3.8.2009, 23:00 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 379
Регистрация: 30.4.2005

Репутация: нет
Всего: 1



да только функцию воврашения значения по индексу который мне нужен. Просто вектор использую в место массива мне так удобнее.
PM MAIL   Вверх
andrew_121
Дата 3.8.2009, 23:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Кодофей
****


Профиль
Группа: Завсегдатай
Сообщений: 3448
Регистрация: 3.1.2008

Репутация: 3
Всего: 33



Remiznik, Ну вот тебе каркас вектора использующего проецирование файла в память. Допиши и используй на здоровье.

Добавлено через 9 минут и 41 секунду
Щас поэкспериментирую, любопытно smile 


--------------------
Удалил аккаунт. Прощайте!
PM MAIL   Вверх
andrew_121
Дата 4.8.2009, 01:00 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Кодофей
****


Профиль
Группа: Завсегдатай
Сообщений: 3448
Регистрация: 3.1.2008

Репутация: 3
Всего: 33



В общем вот что получилось.
Код

#include <io.h>
#include <fcntl.h>

#include <string>
#include <cassert>
#include <iostream>
#include <fstream>
#include <exception>

#ifdef WIN32
#  include "glibc/mman.h"
#else
#  include <sys/mman.h>
#endif

class bad_index : public std::exception {
public:
    bad_index() throw() : std::exception() {}
    virtual ~bad_index() {}
};

class not_init : public std::exception {
public:
    not_init() throw() : std::exception() {}
    virtual ~not_init() {}
};

template<typename T> class MyVector {
public:
    MyVector(const std::string& fn):_fd(-1), _fs(0), _count(0), _fn(fn), _ptr(NULL) {}
    virtual ~MyVector() {}
    /*  */
    bool good() const { return _fd != -1; }
    int count() const {
        if ( _fd < 0 ) {
            throw not_init();
        }
        return _count;
    }
    /*  */
    bool init() {
        _fd = open(_fn.c_str(), _O_BINARY|_O_RDONLY);
        if ( _fd < 0 ) return false;
        
        lseek(_fd, 0L, SEEK_END);
        _fs = tell(_fd);
        lseek(_fd, 0L, SEEK_SET);
        
        _count = _fs/sizeof(T);
        
        _ptr = (char*)mmap(NULL, _fs, PROT_READ, MAP_PRIVATE, _fd, 0);
        return _ptr != NULL;
    }
    void free() {
        if ( _ptr ) {
            munmap(_ptr, _fs);
            _ptr = NULL;
        }
        if ( _fd > 0 ) {
            close(_fd);
            _fd = -1;
        }
    }
    const T& operator[] (int idx) const {
        if ( idx < 0 || idx > _count ) {
            throw bad_index();
        }
        return *(const T*)(_ptr+idx*sizeof(T));
    }
protected:
    int _fd;
    int _fs;
    int _count;
    std::string _fn;
    char* _ptr;
};

struct mystruct {
    int param1;
    int param2;
};

void create_file(const std::string& fn, int count) {
    std::ofstream file(fn.c_str(), std::ios::binary);
    if ( !file.good() ) return;
    
    mystruct data;
    while ( count-- ) {
        data.param1 = data.param2 = rand();
        
        file.write((const char*)&data, sizeof(data));
    }
    
    file.close();
}

int main(int argc, const char **argv) {

    const int count = 1024*1024*100;
    const std::string filename("data.dat");
    create_file(filename, count);

    MyVector<mystruct> vec(filename);
    mystruct data;
    
    assert(vec.init());
    
    try {
        int cnt = vec.count();
        assert(cnt == count);
        int idx = 0;
    
        while ( cnt-- ) {
            data = vec[idx++];
        }
    }
    catch ( const bad_index& e ) {
        std::cout << "bad_index" << std::endl;
    }
    catch ( const not_init& e ) {
        std::cout << "not_init" << std::endl;
    }
    catch ( ... ) {
        std::cout << "who?" << std::endl;
    }
    vec.free();
    
    return 0;
}

Странное поведение под виндавз. Съедает всю память, даже отбирает ее у запущенных программ/процессов. В Linux, все в порядке. Выделяет не больше чем свободной памяти есть. Процессы не обделяет.

Это сообщение отредактировал(а) andrew_121 - 4.8.2009, 21:17


--------------------
Удалил аккаунт. Прощайте!
PM MAIL   Вверх
MAKCim
Дата 5.8.2009, 19:43 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 84
Всего: 207



Цитата(Remiznik @  3.8.2009,  22:35 Найти цитируемый пост)
можно конечно напрямую данные брать из файла на диске но это при большом количестве обращений к файлу очень влияет на время работы. 

1. fread/fwrite используют кэш
2. mmap работает так же как и fread за исключением того, что чтение происходит неявным образом
+readahead, который, к слову реализуется и через fread

Добавлено через 1 секунду
Цитата(Remiznik @  3.8.2009,  22:35 Найти цитируемый пост)
можно конечно напрямую данные брать из файла на диске но это при большом количестве обращений к файлу очень влияет на время работы. 

1. fread/fwrite используют кэш
2. mmap работает так же как и fread за исключением того, что чтение происходит неявным образом
+readahead, который, к слову реализуется и через fread




--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
andrew_121
Дата 5.8.2009, 21:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Кодофей
****


Профиль
Группа: Завсегдатай
Сообщений: 3448
Регистрация: 3.1.2008

Репутация: 3
Всего: 33



Цитата(MAKCim @  5.8.2009,  19:43 Найти цитируемый пост)
1. fread/fwrite используют кэш

Да.
Но если учесть что нужен произвольный доступ, не думаю что кэш будет работать при большом объеме файла.


Цитата(MAKCim @  5.8.2009,  19:43 Найти цитируемый пост)
readahead

Не знал что есть такое. smile  Спасибо!


--------------------
Удалил аккаунт. Прощайте!
PM MAIL   Вверх
MAKCim
Дата 6.8.2009, 20:39 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 84
Всего: 207



Цитата(andrew_121 @  5.8.2009,  21:46 Найти цитируемый пост)
не думаю что кэш будет работать при большом объеме файла.

setvbuf


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
andrew_121
Дата 6.8.2009, 21:14 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Кодофей
****


Профиль
Группа: Завсегдатай
Сообщений: 3448
Регистрация: 3.1.2008

Репутация: 3
Всего: 33



Цитата(MAKCim @  6.8.2009,  20:39 Найти цитируемый пост)
setvbuf 

Нужно экспериментировать.


--------------------
Удалил аккаунт. Прощайте!
PM MAIL   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С/С++: Программирование под Unix/Linux"
xvr
  • Проставьте несколько ключевых слов темы, чтобы её можно было легче найти.
  • Не забывайте пользоваться кнопкой "Код".
  • Вопросы мобильной разработки тут
  • Телепатов на форуме нет! Задавайте чёткий, конкретный и полный вопрос. Указывайте полностью ошибки компилятора и компоновщика.
  • Новое сообщение должно иметь прямое отношение к разделу форума. Флуд, флейм, оффтопик запрещены.
  • Категорически запрещается обсуждение вареза, "кряков", взлома программ и т.д.

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, xvr.

 
 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Программирование под Unix/Linux | Следующая тема »


 




[ Время генерации скрипта: 0.0862 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.