Поиск размера файла на C

#c #unix

#c #unix

Вопрос:

Мне было интересно, было ли какое-либо значительное увеличение производительности при использовании sys / stat.h по сравнению с fseek() и и ftell()?

Комментарии:

1. Вы пробовали писать небольшие программы для каждого метода и самостоятельно измеряли скорость?

Ответ №1:

Выбирая между fstat() и fseek()/ftell() комбинацией, особой разницы не будет. Одиночный вызов функции должен быть немного быстрее, чем двойной вызов функции, но разница не будет большой.

Выбор между stat() и комбинацией — не очень справедливое сравнение. Для комбинированных вызовов тяжелая работа была проделана при открытии файла, поэтому информация об индексе легко доступна. stat() Вызов должен проанализировать путь к файлу, а затем сообщить о том, что он находит. Это почти всегда должно быть медленнее — если только вы все равно не открыли файл недавно, так что ядро хранит большую часть информации в кэше. Даже в этом случае поиск по имени пути, требуемый stat() , вероятно, сделает это медленнее, чем комбинация.

Ответ №2:

Если вы не уверены, попробуйте!

Я только что закодировал этот тест. Я сгенерировал 10000 файлов по 2 КБ каждый и перебрал их все, запрашивая их размер файла.

Результаты на моей машине путем измерения с помощью команды «time» и выполнения в среднем 10 запусков:

  • fseek / версия fclose: 0,22 секунды
  • версия статистики: 0.06 секунд

Итак, победитель (по крайней мере, на моей машине): статистика!

Вот тестовый код:

 #include <stdio.h>
#include <sys/stat.h>

#if 0 
size_t getFileSize(const char * filename)
{
    struct stat st;
    stat(filename, amp;st);
    return st.st_size;
}
#else
size_t getFileSize(const char * filename)
{
    FILE * fd=fopen(filename, "rb");
    if(!fd)
        printf("ERROR on file %sn", filename);

    fseek(fd, 0, SEEK_END);
    size_t size = ftell(fd);
    fclose(fd);
    return size;
}
#endif

int main()
{   
    char buf[256];
    int i, n;
    for(i=0; i<10000;   i)
    {   
        sprintf(buf, "file_%d", i);
        if(getFileSize(buf)!= 2048)
            printf("WRONG!n");
    }
    return 0;
}
  

Ответ №3:

Логически можно было бы предположить, что fseek() при запросе поиска до конца файла используется статистика, чтобы узнать, как далеко искать, или, скорее, где находится конец файла.

Это было бы fseek медленнее, чем прямое использование средств, и это также требует от вас fopen в первую очередь доступа к файлу.

Тем не менее, любая разница в производительности, вероятно, будет незначительной, и если вам все равно по какой-то причине потребуется открыть файл, fseek / ftell , вероятно, значительно улучшит читаемость вашего кода.

Ответ №4:

Для статистики.h вы в основном хотите использовать его для определения статистики файла. Например, если вы хотите определить, является ли это файлом или каталогом и т.д.

Однако, если вы хотите выполнить манипуляции с файлом, то вы, вероятно, захотите использовать ftell () и fseek(). То есть вы фактически выполняете манипуляции с самим файловым потоком.

Итак, с точки зрения производительности, это действительно то, что вам нужно.

Надеюсь, это поможет 🙂 Приветствия!

Ответ №5:

В зависимости от обстоятельств, stat() может быть в сто раз быстрее, чем seek()/tell() . В настоящее время я играюсь с sshfs / FUSE и получение размера файла в несколько тысяч файлов с помощью seek()/tell() занимает более минуты, выполнение этого с помощью stat() занимает секунду. Таким образом, разница довольно велика при работе через sshfs / FUSE.