На главную Наши проекты:
Журнал   ·   Discuz!ML   ·   Wiki   ·   DRKB   ·   Помощь проекту
ПРАВИЛА FAQ Помощь Участники Календарь Избранное RSS
msm.ru
Обратите внимание:
1. Прежде чем начать новую тему или отправить сообщение, убедитесь, что вы не нарушаете правил форума!
2. Обязательно воспользуйтесь поиском. Возможно, Ваш вопрос уже обсуждали. Полезные ссылки приведены ниже.
3. Темы с просьбой выполнить какую-либо работу за автора в этом разделе не обсуждаются.
4. Используйте теги [ code=cpp ] ...текст программы... [ /code ] для выделения текста программы подсветкой.
5. Помните, здесь телепатов нет. Старайтесь формулировать свой вопрос максимально грамотно и чётко: Как правильно задавать вопросы
6. Запрещено отвечать в темы месячной и более давности без веских на то причин.

Полезные ссылки:
user posted image FAQ Сайта (C++) user posted image FAQ Форума user posted image Наши Исходники user posted image Поиск по Разделу user posted image MSDN Library Online (Windows Driver Kit) user posted image Google

Ваше мнение о модераторах: user posted image B.V.
Модераторы: B.V.
Страницы: (5) [1] 2 3 ... Последняя » все  ( Перейти к последнему сообщению )  
> Проецируемые на память файлы , быстродействие и т.д.
    Цитата bobjones @
    если я правильно понял, "промапить"

    Об этом можешь почитать у Рихтера

    Эта тема была разделена из темы "как быстрее"
      Цитата bobjones @
      посмотрел. сотворил тоже самое но с использованием мапа.

      вот только ненужно называть проецируемые в память файлы - мапами, совершенно не понятно что ты имел ввиду, а под мапом в с++ подразумевается нечто другое. >:(
        Цитата Snike @
        мапом в с++ подразумевается нечто другое. >:(

        А в RTS (Real-Time Strategy) под мапом понимается совсем другое.
          Цитата
          под мапом в с++ подразумевается нечто другое.
          под "мапом" я подразумевал проецируемые в память файлы
          CreateFileMapping() и MapViewOf File();

          память DDR 256Mb PC3200 Kingston + DDR 512Mb PC3200 Samsung
          винчестер -SamsungSP 0802N 80Gb , 7200 об/мин

          тест проводился следующим образом:
          *создается файл длиной 104857600 б (100 мб ) содержащий цифру , 0 например
          * запоминается системное время
          *файл обрабатывается тестируемой процедурой
          *берется текущее время и вычетается из запомненного
          *проверяется правильность нового содержимого файла

          код № 3:
          ExpandedWrap disabled
            HANDLE hfile=CreateFile("sourcefile.bin",GENERIC_READ|GENERIC_WRITE,0,
            NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);
            if(hfile==(HANDLE)-1)
              { MessageBox(NULL,"error in opening file","error",0);
                return;
               }
            HANDLE hmap=CreateFileMapping(hfile,NULL,PAGE_READWRITE,
            0,0,NULL);
            if(hmap==NULL)
              { MessageBox("NULL,"error in map create","error",0);
                CloseHandle(hfile);
                return;
               }
            DWORD fsh;
            int filesize=GetFileSize(hfile,&fsh);
            filesize+=(((int)fsh)<<32);
            CloseHandle(hfile);
            int fileoffset=0;
             
            while(filesize>0)
            {
            DWORD block=65536;        
            if(filesize<block)
            block=(DWORD)filesize;
             
            PBYTE pbfile=(PBYTE)MapViewOfFile(hmap,FILE_MAP_ALL_ACCESS,
            (DWORD)(fileoffset>>32),0,block);
             
            for(DWORD i=0;i<block;i++)  pbfile[i]=pbfile[i]+5;        //обработка
            UnmapViewOfFile(pbfile);
            filesize-=block;
            }
            CloseHandle(hmap);
            //дальше идет подсчет времени
          Сообщение отредактировано: trainer -
            Цитата Snike @
            а под мапом в с++ подразумевается нечто другое.
            Что именно в С++ понимается под "мапом"? Достаточно указать пункт стандарта.
              bobjones
              Ты сам то понял, что с MapViewOfFile "натворил" :D
              Младший дворд dwFileOffsetLow = 0, старший тоже dwFileOffsetHigh == fileoffset == 0. В результате ты всегда читаешь и звписываешь одни и теже первые 64К. Осюда и "суперскорость", хотя реально скорость чтения с диска обычно не превышает 50 Мб/с и 100Мб должны читаться не менее или около 2 сек.

              Во-вторых, если размер файла заведомо меньше размера ОЗУ, то делать блочную обработку с Map\Unmap никакого смыла нет - лишь дополнительные тормоза (хоть и не столь значительные по сравнению с временем чтения\записи). Да и ждать чудес от MMF тоже не стоит - при последовательной обработке обычно он не дает выигрыша по сравнению с ReadFile\WriteFile блоками до 64К
                Цитата
                Младший дворд dwFileOffsetLow = 0, старший тоже dwFileOffsetHigh == fileoffset == 0.

                точно, ошибка здесь. надо вот так:
                PBYTE pbfile=(PBYTE)MapViewOfFile(hmap,FILE_MAP_ALL_ACCESS,0,(DWORD)(fileoffset&0xFFFFFFFF),block);
                fileoffset+=block;

                однако результаты теста не отменяются: 0.521 - 0.540 секунды.

                привожу полный код:

                ExpandedWrap disabled
                  #include <fstream.h>
                  #include <dateutils.hpp>
                  #include <iostream.h>
                  #pragma hdrstop
                   
                  #pragma argsused
                   
                  createfile(int);
                  bool checkfile(int );
                   
                  //---------------------------------------------------------------------------
                  int main(int argc, char* argv[])
                  {
                  int value=0;
                  createfile(value);
                  char * name="sourcefile.bin";
                  SYSTEMTIME tbegin,tend;
                   
                  GetSystemTime(&tbegin);
                  HANDLE hfile=CreateFile(name,GENERIC_READ|
                  GENERIC_WRITE,0,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);
                  if(hfile==(HANDLE)-1)
                    { MessageBox(NULL,"error in opening file","",0);
                      return
                      0;
                     }
                  HANDLE hmap=CreateFileMapping(hfile,NULL,PAGE_READWRITE,
                  0,0,NULL);
                  if(hmap==NULL)
                    { MessageBox(NULL,"error in map create","",0);
                      CloseHandle(hfile);
                      return 0;
                     }
                  DWORD fsh;
                  int filesize=GetFileSize(hfile,&fsh);
                  filesize+=(((int)fsh)<<32);
                  CloseHandle(hfile);
                  int fileoffset=0;
                  while(filesize>0)
                  {
                  DWORD block=65536;
                  if(filesize<block) block=(DWORD)filesize;
                  PBYTE pbfile=(PBYTE)MapViewOfFile(hmap,FILE_MAP_ALL_ACCESS,
                  0,(DWORD)(fileoffset&0xFFFFFFFF),block);
                  fileoffset+=block;
                  for(DWORD i=0;i<block;i++)  pbfile[i]=pbfile[i]+5;
                  UnmapViewOfFile(pbfile);
                   
                  filesize-=block;
                  }
                  CloseHandle(hmap);
                  GetSystemTime(&tend);
                   
                  cout << tend.wSecond - tbegin.wSecond << "\n" << tend.wMilliseconds-tbegin.wMilliseconds;
                  if (checkfile(value+5)) cout << "\nYES!";
                  cin >> name;
                  }
                   
                  //---------------------------------------------------------------------------
                  createfile(int n)
                  {
                  ofstream cf;
                  cf.open("sourcefile.bin",ios::out | ios::binary);
                  for(int i=0;i<104857600;i++)
                  cf.put(n);
                  cf.close();
                  }
                  //-----------------------------------------------------------------
                  bool checkfile(int n)
                  {
                  ifstream in;
                  char *sym;
                  in.open("sourcefile.bin",ios::in|ios::binary);
                  int count=0;
                  for(int i=0;i<104857600;i++)
                  {
                  in.get(*sym);
                  if((int)*sym != n)
                   { cout << "\nERROR IN FILE" << count;
                     return 0;
                   }
                   count++;
                  }
                  in.close();
                  }
                  Цитата
                  Возьми реальный ненулевой файл и посмотри, что получится


                  взял , посмотрел. все равно - 0.5 секунды

                  теперь код вот такой:

                  ExpandedWrap disabled
                    #include <fstream.h>
                    #include <dateutils.hpp>
                    #include <iostream.h>
                    #pragma hdrstop
                     
                    //---------------------------------------------------------------------------
                    #pragma argsused
                     
                    createnewfile();
                     
                    int main(int argc, char* argv[])
                    {
                    createnewfile();
                    char * name="sourcefile.bin";
                    SYSTEM_INFO *sinf=new SYSTEM_INFO;
                    SYSTEMTIME tbegin,tend;
                    GetSystemTime(&tbegin);
                     
                    HANDLE hfile=CreateFile(name,GENERIC_READ|
                    GENERIC_WRITE,0,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);
                    if(hfile==(HANDLE)-1)
                      { MessageBox(NULL,"error in opening file","",0);
                        return
                        0;
                       }
                    HANDLE hmap=CreateFileMapping(hfile,NULL,PAGE_READWRITE,
                    0,0,NULL);
                    if(hmap==NULL)
                      { MessageBox(NULL,"error in map create","",0);
                        CloseHandle(hfile);
                        return 0;
                       }
                    DWORD fsh;
                    __int64 filesize=GetFileSize(hfile,&fsh);
                    filesize+=(((int)fsh)<<32);
                    CloseHandle(hfile);
                    __int64 fileoffset=0;
                    while(filesize>0)
                     {
                    DWORD block=sinf->dwAllocationGranularity;
                    if(filesize<block) block=(DWORD)filesize;
                     
                    PBYTE pbfile=(PBYTE)MapViewOfFile(hmap,FILE_MAP_ALL_ACCESS,
                    (DWORD)(fileoffset>>32),(DWORD)(fileoffset&0xFFFFFFFF),block);
                     
                    if(pbfile==NULL) {
                                      MessageBox(NULL,"Error in view","error",0);
                                      return 0;
                                      }
                    fileoffset+=block;
                    for(DWORD i=0;i<block;i++)  pbfile[i]=pbfile[i]+5;
                    UnmapViewOfFile(pbfile);
                    filesize-=block;
                     }
                    delete sinf;
                    CloseHandle(hmap);
                    GetSystemTime(&tend);
                    cout << tend.wSecond - tbegin.wSecond << "\n" << tend.wMilliseconds-tbegin.wMilliseconds
                    << "\n\nEnd of test";
                    cin >> name;
                    }
                     
                    //---------------------------------------------------------------------------
                    createnewfile()
                    {
                    cout << "creating test file...\n";
                    ofstream cf;
                    cf.open("sourcefile.bin",ios::out | ios::binary);
                    for(int i=0;i<104857600;i++)
                    cf.put(random(256));       // теперь в файл пишутся [псевдо]случайные числа
                    cf.close();
                    cout << "done.\n\n";
                    }


                  Добавлено
                  я намеренно опустил проверку файла после преобразования чтобы не загромождать код
                    Представление о преимуществах MMF по скорости это очень распространенный миф, основанный на голословных отрывочных фразах из официальных док MS и на некорректных сравнениях некоторых горе-популяризаторов. Последовательное чтение данных с диска путем MMF в принципе не может быть быстрее правильно организованного блочного чтения через ReadFile, а на деле часто оказывается чуть медленее, т.к. весь MMF основан на исключениях отказа страниц, обработка которых занимает заметное время.

                    С записью\копированием дело обстоит несколько сложнее, т.к. сюда замешиваются доп.факторы -
                    особенности работы HDD и хитрости ОС. Во-первых, при MMF данные после UnmapView не сразу записываются на диск и могут находиться в ОЗУ неопределенно долго. Считать ли это преимуществом MMF - вопрос спорный, т.к. накопленные страницы могут начать выгружаться на диск в любой неподходящий момент. Например, если прога после копирования переходит в режим ожидания или занимается длительными вычислениями, то это м.б. незаметно, а вот если нужно обработать еще десяток таких же файлов (или размер одного копируемого файла превышает размер ОЗУ), то тут отложенная запись может проявить себя во всей красе. Если же сравнивать по честному и перед UnmapView вызывать FlushView, то время копирования будет примерно таким же как и при обычном Read\Write c тем же размером буфера.

                    Во-вторых, размер буфера при копировании должен быть больше, чем при простом чтении. Но устремлять размер в "бесконечность" смысла нет, т.к. тут есть разумный предел. При чередовании чтения и записи HDD вынужден каждый раз позиционировать головки, на что уходит не менее 60(с)/7200(об/мин) = 8 мс. Поэтому при размере блока 64К у нас только на одно позиционирование в данном случае уходит (100М/64К)*8мс ~ 13 сек. Вычтем 13 из 18-19 сек и получим разумные 5-6 сек = 2*(2.5-3). Но чтобы снизить потери скажем до 5-10%, достаточно при макс.скорости чтения ~50 Мб/с увеличить размер буфера до (10-20)*8(мс)*50(Мб/с) =4-8 Мб (ну можно с запасом до 10-20 Мб - дальше просто смысла нет).

                    Однако при увеличении размера буфера может проявиться еще одна "хитрость" - скорость обычного буферированного чтения может несколько снизиться из-за возрастания числа промахов быстрого чтения из файлового кэша. Например, в WinXP максимальная скорость чтения получается при размере буфера до 64К, а затем резко увеличивается число кэш-промахов и скорость чтения несколько падает (вообще-то это выглядит довольно глуповато - пытаться лезть в кэш, когда размер считываемых данных превышает размер упреждающего чтения). Но если использовать FILE_FLAG_NO_BUFFERING, то ничего подобного не происходит и скорость копирования оказывается всегда выше чем у MMF c FlushView. Ну а если без Flush, то конечно MMF за счет отложенной записи может формально показывать вдвое лучшие результаты.
                    Сообщение отредактировано: leo -
                      все же у filemapping должны быть плюсы - например достаточно простой неоднократный доступ к файлу.
                      допустим, алгоритм, проходящий файл несколько раз. отобразили на память , поработали, записали на диск. по-любому быстрей чем каждый раз читать/ писать на винт.
                        Цитата bobjones @
                        все же у filemapping должны быть плюсы - например достаточно простой неоднократный доступ к файлу.
                        допустим, алгоритм, проходящий файл несколько раз. отобразили на память , поработали, записали на диск. по-любому быстрей чем каждый раз читать/ писать на винт.

                        :yes: :yes:
                        Но для просто копирования, обычный метод чуууточку шустрее.
                          Цитата bobjones @
                          допустим, алгоритм, проходящий файл несколько раз. отобразили на память , поработали, записали на диск. по-любому быстрей чем каждый раз читать/ писать на винт.

                          Зато есть один здоровенный минус: файл > 4Gb на 32-битной архитектуре не обработать.
                            Цитата linuxfan @
                            Зато есть один здоровенный минус: файл > 4Gb на 32-битной архитектуре не обработать.

                            Глупость
                              До тех пор, пока не напорешься так и будешь думать, что глупость.
                              На самом деле, при использовании mmap'а теряется еще одна возможность: потоковая обработка.
                                32 разрядность архитектуры тут не причем...
                                Цитата linuxfan @
                                До тех пор, пока не напорешься так и будешь думать, что глупость.

                                Изв. но почему-то не напоролся :rolleyes:
                                1 пользователей читают эту тему (1 гостей и 0 скрытых пользователей)
                                0 пользователей:


                                Рейтинг@Mail.ru
                                [ Script execution time: 0,0486 ]   [ 15 queries used ]   [ Generated: 13.05.25, 12:35 GMT ]