代码之家  ›  专栏  ›  技术社区  ›  Kasper

如何使用printf显示off-t、nlink-t、size-t等特殊类型?

  •  27
  • Kasper  · 技术社区  · 16 年前

    在我的程序中,我统计他们想要的文件并发送数据。统计的字段 struct 是否所有特殊类型:

    struct stat {
      dev_t     st_dev;     /* ID of device containing file */
      ino_t     st_ino;     /* inode number */
      mode_t    st_mode;    /* protection */
      nlink_t   st_nlink;   /* number of hard links */
      uid_t     st_uid;     /* user ID of owner */
      gid_t     st_gid;     /* group ID of owner */
      dev_t     st_rdev;    /* device ID (if special file) */
      off_t     st_size;    /* total size, in bytes */
      blksize_t st_blksize; /* blocksize for file system I/O */
      blkcnt_t  st_blocks;  /* number of 512B blocks allocated */
      time_t    st_atime;   /* time of last access */
      time_t    st_mtime;   /* time of last modification */
      time_t    st_ctime;   /* time of last status change */
    };
    

    我问题的相关代码如下:

    len = snprintf( statbuf, STAT_BUFFER_SIZE,
      "%crwxrwxrwx %lu %u %u %lld %s %s\r\n",
      S_ISDIR( filestats.st_mode ) ? 'd' : '-',
      (unsigned long ) filestats.st_nlink,
      filestats.st_uid,
      filestats.st_gid,
      (unsigned long long ) filestats.st_size,
      date,
      filename);
    

    如何以便携式和高效的方式打印这些类型?起初,我没有通过猜测正确的格式说明符来进行强制转换。除了令人讨厌的编程习惯之外,这也意味着我的代码在32位系统上无法工作。现在,对于演员表,它似乎可以工作,但是在多少个平台上?

    1 回复  |  直到 11 年前
        1
  •  26
  •   Community Mohan Dere    9 年前

    没有一种完全可移植的方式来完成这项工作,这很麻烦。

    C99为内置类型提供了一种机制,例如 size_t %zu 符号(还有一些额外的,类似的限定符)。

    它还提供 <inttypes.h> 包含宏(如prix32)的头,用于定义打印32位十六进制常量的正确限定符(在本例中):

    printf("32-bit integer: 0x%08" PRIX32 "\n", var_of_type_int32_t);
    

    对于系统定义的类型(例如由posix定义的类型),afaik,没有好的方法来处理它们。所以,我要做的是对一个“安全”的转换进行一个快速的猜测,然后打印相应的内容,包括演员表,这就是您在问题中所阐述的内容。这是令人沮丧的,但没有更好的方法,我知道。如果有疑问,并且使用c99,那么转换为“无符号长整型”就非常好了;可能有一种情况是使用强制转换 uintmax_t 和Prixmax或同等产品。

    或者,作为 FUZxxl reminded 我,你可以用修改器 j 以指示“max”整数类型。例如:

    printf("Maximal integer: 0x%08jX\n", (uintmax_t)var_of_type_without_format_letter);