Как определить размер файла в C?

Как я могу определить размер файла в байтах?

#include <stdio.h>

unsigned int fsize(char* file){
  //what goes here?
}

Ответы

Ответ 1

На основе кода NilObject:

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

off_t fsize(const char *filename) {
    struct stat st; 

    if (stat(filename, &st) == 0)
        return st.st_size;

    return -1; 
}

Изменения:

  • Сделал аргумент имени файла const char.
  • Исправлено определение struct stat, в котором отсутствовало имя переменной.
  • Возвращает -1 при ошибке вместо 0, что было бы неоднозначно для пустого файла. off_t является типом со off_t так что это возможно.

Если вы хотите, чтобы fsize() печатал сообщение об ошибке, вы можете использовать это:

#include <sys/stat.h>
#include <sys/types.h>
#include <string.h>
#include <stdio.h>
#include <errno.h>

off_t fsize(const char *filename) {
    struct stat st;

    if (stat(filename, &st) == 0)
        return st.st_size;

    fprintf(stderr, "Cannot determine size of %s: %s\n",
            filename, strerror(errno));

    return -1;
}

В 32-битных системах вы должны скомпилировать это с опцией -D_FILE_OFFSET_BITS=64, иначе off_t будет содержать значения только до 2 ГБ. Подробности смотрите в разделе "Использование LFS" в разделе " Поддержка больших файлов в Linux".

Ответ 2

Не используйте int. Файлы размером более 2 гигабайт обычно являются грязью в эти дни.

Не используйте unsigned int. Файлы размером более 4 гигабайт являются общими, так как некоторые немного менее распространенные загрязнения

IIRC стандартная библиотека определяет off_t как неподписанное 64-битное целое число, которое все должны использовать. Мы можем переопределить это до 128 бит за несколько лет, когда мы начнем работать с 16 файлами exabyte.

Если вы находитесь в окнах, вы должны использовать GetFileSizeEx - на самом деле он использует подписанное 64-битное целое число, поэтому они начнут сталкиваться с проблемами с 8 файлами exabyte. Глупый Microsoft!: -)

Ответ 3

Решение Matt должно работать, за исключением того, что это С++ вместо C, и исходный запрос не нужен.

unsigned long fsize(char* file)
{
    FILE * f = fopen(file, "r");
    fseek(f, 0, SEEK_END);
    unsigned long len = (unsigned long)ftell(f);
    fclose(f);
    return len;
}

Исправлена ​​ваша скобка для вас.;)

Обновление: это не лучшее решение. Он ограничивается файлами размером 4 ГБ в Windows, и это, вероятно, медленнее, чем просто использование определенного для платформы вызова типа GetFileSizeEx или stat64.

Ответ 4

** Не делайте этого (почему?):

Цитата стандартного документа C99, который я нашел в Интернете: "Установка индикатора положения файла в конец файла, как и в файле fseek (файл, 0, SEEK_END), имеет поведение undefined для бинарного потока (из-за возможного завершающие нулевые символы) или для любого потока с зависящей от состояния кодировкой, которая не обязательно заканчивается в исходном состоянии сдвига. **

Измените определение на int, чтобы сообщения об ошибках могли быть переданы, а затем используйте fseek() и ftell() для определения размера файла.

int fsize(char* file) {
  int size;
  FILE* fh;

  fh = fopen(file, "rb"); //binary mode
  if(fh != NULL){
    if( fseek(fh, 0, SEEK_END) ){
      fclose(fh);
      return -1;
    }

    size = ftell(fh);
    fclose(fh);
    return size;
  }

  return -1; //error
}

Ответ 5

Если вам хорошо с помощью библиотеки std c:

#include <sys/stat.h>
off_t fsize(char *file) {
    struct stat filestat;
    if (stat(file, &filestat) == 0) {
        return filestat.st_size;
    }
    return 0;
}

Ответ 6

POSIX

Стандарт POSIX имеет свой собственный метод для получения размера файла.
Включите заголовок sys/stat.h для использования функции.

конспект

  • Получить статистику файла, используя stat(3).
  • Получите свойство st_size.

Примеры

Примечание. Размер ограничен 4GB. Если не Fat32 система Fat32 тогда используйте 64-битную версию!

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

int main(int argc, char** argv)
{
    struct stat info;
    stat(argv[1], &info);

    // 'st' is an acronym of 'stat'
    printf("%s: size=%ld\n", argv[1], info.st_size);
}
#include <stdio.h>
#include <sys/stat.h>

int main(int argc, char** argv)
{
    struct stat64 info;
    stat64(argv[1], &info);

    // 'st' is an acronym of 'stat'
    printf("%s: size=%ld\n", argv[1], info.st_size);
}

ANSI C (стандарт)

ANSI C не предоставляет прямой способ определения длины файла.
Нам придется использовать наш разум. Сейчас мы будем использовать подход поиска!

конспект

  • Найдите файл до конца, используя fseek(3).
  • Получить текущую позицию, используя ftell(3).

пример

#include <stdio.h>

int main(int argc, char** argv)
{
    FILE* fp = fopen(argv[1]);
    int f_size;

    fseek(fp, 0, SEEK_END);
    f_size = ftell(fp);
    rewind(fp); // to back to start again

    printf("%s: size=%ld", (unsigned long)f_size);
}

Если файл stdin или труба. POSIX, ANSI C не будет работать.
Будет возвращаться 0 если файл представляет собой канал или стандартный stdin.

Мнение: Вы должны вместо этого использовать стандарт POSIX. Потому что он имеет поддержку 64 бит.

Ответ 7

И если вы создаете приложение Windows, используйте API GetFileSizeEx, поскольку ввод/вывод файлов CRT бесполезен, особенно для определения файла длина из-за особенностей файловых представлений в разных системах;)

Ответ 8

Быстрый поиск в Google нашел метод, использующий fseek и ftell, и поток с этим вопросом с ответами, что это невозможно сделать в просто C по-другому.

Вы можете использовать библиотеку переносимости, например NSPR (библиотека, которая активирует Firefox) или проверьте его реализация (довольно волосатая).

Ответ 9

Я использовал этот набор кода для поиска длины файла.

//opens a file with a file descriptor
FILE * i_file;
i_file = fopen(source, "r");

//gets a long from the file descriptor for fstat
long f_d = fileno(i_file);
struct stat buffer;
fstat(f_d, &buffer);

//stores file size
long file_length = buffer.st_size;
fclose(i_file);

Ответ 10

Попробуйте это -

fseek(fp, 0, SEEK_END);
unsigned long int file_size = ftell(fp);
rewind(fp);

Что это значит, прежде всего, ищите конец файла; затем сообщите, где находится указатель файла. Наконец (это необязательно) он перематывается обратно в начало файла. Обратите внимание, что fp должен быть двоичным потоком.

file_size содержит количество байтов, содержащихся в файле. Обратите внимание, что поскольку (согласно climits.h) беззнаковый длинный тип ограничен 4294967295 байтами (4 гигабайта), вам нужно будет найти другой тип переменной, если вы, вероятно, будете иметь дело с файлами, большими, чем это.

Ответ 11

Здесь простая и понятная функция, которая возвращает размер файла.

long get_file_size(char *path)
{
    FILE *fp;
    long size = -1;
    /* Open file for reading */
    fp = fopen(path, "r");
    fseek(fp, 0, SEEK_END);
    size = ftell(fp); 
    fp.close();
    return 
}

Ответ 12

Для этого мы будем использовать fseek(3), ftell(3)/ ftello(3) которые определены в <stdio.h>.
Этот метод работает как в Linux, так и в Windows!

#include <stdio.h>
#include <stdint.h>

int main()
{
  // On 32bit
  FILE* fp = fopen("sample.txt", "r");

  /* These 3 functions are called "The seek approach" */
  fseek(fp, 0, SEEK_END);
  uint32_t size = ftell(fp);
  rewind(fp); // fseek(fp, 0, SEEK_SET);

  // On 64bit
  fseek(fp, 0, SEEK_END);
  uint64_t size = ftell(fp);
  rewind(fp);
}

32- битный метод может рассчитывать до 4GB размера файла, также как ограничение размера файла Fat32.
Примечание: если ввод stdin/pipe, метод не будет работать.

Ответ 13

У меня есть функция, которая хорошо работает только с stdio.h. Мне это очень нравится, оно работает очень хорошо и довольно лаконично:

size_t fsize(FILE *File) {
    size_t FSZ;
    fseek(File, 0, 2);
    FSZ = ftell(File);
    rewind(File);
    return FSZ;
}

Ответ 14

Вам понадобится использовать библиотечную функцию для получения сведений о файле. Поскольку C полностью независима от платформы, вам нужно сообщить нам, какую платформу/операционную систему вы разрабатываете!

Ответ 15

Рассматривая вопрос, ftell может легко получить количество байтов.

  long size ;
  size = ftell(FILENAME);
  printf("total size is %ld bytes",size);

Ответ 16

Вы можете открыть файл, перейти к 0 смещению относительно нижней части файла с помощью

#define SEEKBOTTOM   2

fseek(handle, 0, SEEKBOTTOM)  

значение, возвращаемое из файла fseek, - это размер файла.

Я долгое время не записывал код на C, но я думаю, что он должен работать.