C ++ - Erkennung von Konstanten zur Kompilierungszeit

Es gibt Fälle, in denen eine Bibliotheksquelle verfügbar ist und im Allgemeinen variable Parameter unterstützt werden müssen. In der Praxis sind diese Parameter jedoch häufig Konstanten.

Dann kann es möglich sein, Dinge durch spezielle Behandlung konstanter Parameter zu optimieren (z. B. statische Arrays anstelle der Heap-Zuweisung zu verwenden), aber dafür ist es notwendig zu bestimmen, ob etwas zuerst eine Konstante ist (oder vielleicht einige Makros zu definieren, aber es ist weniger) praktisch)

So hier ist eine funktionierende Implementierung.

Update: auch hier:http: //codepad.org/ngP7Kt1

Ist es wirklich ein gültiges C ++?ibt es eine Möglichkeit, diese Makros loszuwerden? (is_const () kann keine Funktion sein, da die Funktionsabhängigkeit im Array-Größenausdruck nicht funktioniert; es kann auch keine Vorlage sein, da dies auch keinen variablen Parameter akzeptiert.)

Aktualisieren Hier ist ein Update mit etwas mehr Verwendungszweck. Der Compiler generiert keinen Code für dasif(N==0) branch ifN ist nicht 0. Auf die gleiche Weise können wir auf völlig andere Datenstrukturen umschalten, wenn wir wollen. Sicher ist es nicht perfekt, aber deshalb habe ich diese Frage gestellt.


 #include <stdio.h><p></p>

struct chkconst {
  struct Temp { Temp( int x ) {} };
  static char chk2( void* ) { return 0; }
  static int  chk2( Temp  ) { return 0; }
};

#define is_const_0(X) (sizeof(chkconst::chk2(X))<sizeof(int))
#define is_const_0i(X) (sizeof(chkconst::chk2(X))>sizeof(char))
#define is_const(X) is_const_0( (X)^((X)&0x7FFFFFFF) )

#define const_bit(X1,bit) (is_const_0i((X1)&(1<<bit))<<bit)
#define const_nibl(X1,bit) const_bit(X1,bit) | const_bit(X1,(bit+1)) | const_bit(X1,(bit+2)) | const_bit(X1,(bit+3)) 
#define const_byte(X1,bit) const_nibl(X1,bit) | const_nibl(X1,(bit+4))
#define const_word(X1,bit) const_byte(X1,bit) | const_byte(X1,(bit+8))
#define const_uint(X1) const_word(X1,0) | const_word(X1,16)
#define const_switch_word( X1, X2 ) (is_const(X1) ? const_word(X1,0) : X2)
#define const_switch_uint( X1, X2 ) (is_const(X1) ? const_uint(X1) : X2)

const int X1 = 222;
const int X2 = printf( "" ) + 333;

char Y1[ const_switch_word(X1,256) ];
char Y2[ const_switch_word(X2,256) ];

template< int N > 
void test( int N1 ) {
  char _buf[N>0?N:1];
  char* buf = _buf;
  if( N==0 ) {
    buf = new char[N1];
  }
  printf( "%08X %3i %3i\n", buf, N, N1 );
}

#define testwrap(N) test< const_switch_word(N,0) >( N )

int main( void ) {
  printf( "%i %i %i\n", X1, is_const(X1), sizeof(Y1) );
  printf( "%i %i %i\n", X2, is_const(X2), sizeof(Y2) );
  testwrap( X1 );
  testwrap( X2 );
}

Antworten auf die Frage(6)

Ihre Antwort auf die Frage