C言語の文法「宣言は置換規則」

最近思うんだけれど、C言語の文法って
「宣言は置換規則」
っていう発想がところどころみられるよね。
たとえば、古いK&Rの関数定義なら

#include <stdio.h>

/* funcの定義 */
char func(x,y)
int x;
double y;
{
  return 'B';
}
/* funcの利用 */
main() {
  int x; /* xはintに置換される */
  double y; /* yはdoubleに置換される */
  x = 1;
  y = 2.0;
  printf("%c", func(x,y)); /* func(x,y)がcharに置換される、と考えることもできる */
}

それから、悪名高いポインタと配列の定義。

#include <stdio.h>
#include <string.h>
int main() {
  int ary[10]; /* なぜか、int[10] ary;ではない */
  char ch;
  char *ptr0, *ptr1; /* なぜか、int* ptr0, ptr1;ではない */
  int (*comp)(const char *, const char *); /* int(*)(const char*, const char*) comp; でいいじゃん! */
  /* なぜかというと */
  ary[2] = 4;
  printf("%d", ary[2]); /* ary[0 <= x < 10]は、intに置換される! */
  ptr1 = &ch;
  *ptr1 = 'A';
  printf("%c", *ptr1); /* *ptr1は、charに置換される! */
  comp = strcmp;
  printf("%d", comp("abc", "abd")); /* comp(...)は、intに置換される! */
  printf("%d", (*comp)("abc", "abd")); /* 上と同じだけど、この書き方だと完璧 */
  return 0;
}

C言語はこの考え方のせいでだいぶ損してるように思うんだけど僕だけでしょうか。