【问题标题】:Unixy way of sorting C prototypes alphabeticallyUnixy按字母顺序排序C原型的方法
【发布时间】:2014-06-25 06:48:54
【问题描述】:

假设你有一个 C 函数原型列表,每行一个,比如

void   foo(void);
struct baz *zap(void (*callback)(void));
long long blurb(long i);
long double sinus(long double arg);
sometype_t somefunc(void);

按函数名排序结果为

long long blurb(long i);
void   foo(void);
long double sinus(long double arg);
sometype_t somefunc(void);
struct baz *zap(void (*callback)(void));

据我阅读 sort(1) 手册,这不能使用 -k 选项进行排序,因为函数标识符有时是第二个单词,有时是第三个单词(让我们忽略函数标识符更远的情况对,就像拼写结构时一样)。

但我知道函数标识符是行上第一个 '(' 标记之前的字符串。有人知道对此进行排序的统一方法吗?Unixy := 单行过滤器/管道 . 我可能会破解一个丑陋的 perl 解决方案,删除无趣的左侧部分、排序和恢复左侧部分,但这远非单行。

【问题讨论】:

  • 为什么要按第一个字母而不是功能对函数进行分组?
  • 也许使用 awk 将函数名交换/复制到第一个位置,然后通过管道对其进行排序,这样您就可以排序 `foo: void foo(void)..."
  • 当然,在 perl 中,一切都可以是一条线——只是有时它是一条非常很长的线!
  • @Lundin 因为函数已经有名称前缀,如 fooStart、fooStop、fooGet、fooSet。此外,“相同的功能”是一个相当随意和模棱两可的标准。字母顺序在插入原型的位置没有歧义。在这种顺序对编译器无关紧要的情况下,我喜欢硬性规定。
  • 请注意,标准 C 函数 signal() 有一个类似于 void (*signal(int sig, void (*func)(int)))(int); 的原型,它与您的期望不符。没有一种简单的方法可以在单行中做到这一点——这不是一个简单的问题,因为 C 语法并不简单。事实上,我认为没有一种简单的方法可以在多行脚本中执行此操作 - 仅分析行以提取函数名称是一项艰巨的工作。

标签: c sorting unix function-prototypes


【解决方案1】:

但我知道函数标识符是该行第一个'('标记之前的字符串

我进行此类排序任务的常用方法是使用sed 和一个好的正则表达式在输入中插入一个唯一的分隔符,我以后可以将它与sort 一起使用。分拣后可以去掉分隔符。所以:

  1. 在函数标识符前插入(
  2. 使用( 作为分隔符按第二列排序。
  3. 从该行中删除第一个(

以下内容:

sed 's/\([a-zA-Z0-9_]*(\)/(\1/' | sort -t'(' -k2 | sed 's/(//'

使用以下输入:

void   foo(void);
struct baz *zap(void (*callback)(void));
long long blurb(long i);
long double sinus(long double arg);
sometype_t somefunc(void);

outputs on repl:

long long blurb(long i);
void   foo(void);
long double sinus(long double arg);
sometype_t somefunc(void);
struct baz *zap(void (*callback)(void));

【讨论】:

    【解决方案2】:

    使用the Schwartz:

    perl -pE 'm!([a-zA-Z_][a-zA-Z0-9_]*)\(! && print "$1:"' | # decorate
    sort |                                                    # sort
    perl -pE 's!^([a-zA-Z_][a-zA-Z0-9_]*):!!'                 # undecorate
    

    【讨论】:

      【解决方案3】:

      使用awktrcutsort

      tr -s ' ' file | cut -d '(' -f 1 | awk '{print($NF" "$0)}' | cut -d ' ' -f1 | tr -d '*' | sort
      
      1. 挤压空间重复
      2. 使用 ( 分隔符从行中剪切第一个字段
      3. 获取最后一个字段、函数名,先复制
      4. 使用空格分隔符仅剪切第一个字段
      5. 删除所有*,指针返回字符
      6. 排序

      【讨论】:

      • 只剩下函数标识符。这个想法是按行对整个输入进行排序。
      猜你喜欢
      • 1970-01-01
      • 2020-03-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-04-16
      • 1970-01-01
      相关资源
      最近更新 更多