Can C sort at compile time?

我只是一个虾纸丫 提交于 2020-01-02 03:24:31

问题


Is it possible to sort elements at compile time in C?

Syntax is of secondary importance, I was thinking of a macro like this:

SORT(9, -1, 12, 4)   // expands to: -1, 4, 9, 12
SORT(dog, cat, cow)  // expands to: cat, cow, dog

but I won't frown at any API as long as it sorts without issuing a single CPU instruction.

The requirements are pretty lax:

  • Pure C, no C++. Staying within the C standard would be nice but established language extensions are fair game.
  • Compiler is the only tool allowed. Unix sort or home-brewed code generators are not welcome as they complicate the build step.
  • Any element type is fine. It's OK if it can sort e.g. numbers but not strings.
  • Fixed-length API is fine. Having to call SORT_5 to sort 5 elements is OK.

I realize the solution will probably resort to some language voodoo that barely compiles, I just want to know if it's possible.


回答1:


Here is a macro approach:

#define GET_1_of_3(a, b, c) ((a) < (b) ? ((c) < (a) ? (c) : (a)) : ((c) < (b) ? (c) : (b)))
#define GET_2_of_3(a, b, c) ((c) > (a) && (c) < (b) || (c) < (a) && (c) > (b) ? (c) : ((b) > (a) && (b) < (c) || (b) < (a) && (b) > (c) ? (b) : (a)))
#define GET_3_of_3(a, b, c) ((a) > (b) ? ((c) > (a) ? (c) : (a)) : ((c) > (b) ? (c) : (b)))
#define SORT_3(a, b, c) GET_1_of_3(a, b, c),GET_2_of_3(a, b, c),GET_3_of_3(a, b, c)

void main(){
    int x[3] = { SORT_3(6,2,3) };
    printf("%d, %d, %d", x[0], x[1], x[2]);
}

This works for int and works in C, but it's not possible for strings without const_expr from C++. Obviously, you're in for a lot of macro-writing to support a large number of SORT_X.




回答2:


Let's consider sorting numbers that can only be 0 or 1. For two numbers, SORT2 in the following code can sort them:

#define SORT2(a,b) SORT2_##a##b
#define SORT2_00 0,0
#define SORT2_01 0,1
#define SORT2_10 0,1
#define SORT2_11 1,1

This can of course be expanded to larger ranges and more arguments.




回答3:


Not really, you cannot sort in C at compile time (at least if you want to sort a sufficiently large number of compile-time constant integers; in that case having a 300 macros or functions named SORT_1, SORT_2, ... SORT_300 is not practical, unless you generate these functions or macros, which you do not want to), however....

Pragmatical approach would be to use your own or some other preprocessor (e.g. gpp) and have it do the sort. Or simply, have the numbers in some included file and generate that sorted file (e.g. with a make rule using awk & sort)

You could also consider linking using link-time-optimization to an LTO-compiled libc, using its LTO-optimized qsort. This is not usual, AFAIK, and you have no guarantee that the compiler is smart-enough to inline your LTO qsort etc... (AFAIK, current C compilers don't do that).

If compiling with a recent GCC (4.8, 4.9 or soon 5.0 in march 2015), you could customize it (e.g. with MELT or with your own C++ plugin) to define your __builtin_my_compile_time_sort (or perhaps some _Pragma) to do the job. This is compiler specific (could mean several days of work, unless you know MELT already)

The simplest thing would be to accept slightly complicating the build step. It is not a big deal.



来源:https://stackoverflow.com/questions/29268723/can-c-sort-at-compile-time

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!