Perché sizeof è considerato un operatore?


93

Perché è sizeofconsiderato un operatore e non una funzione?

Quale proprietà è necessaria per qualificarsi come operatore?

Risposte:


181

Perché lo standard C lo dice e ottiene l'unico voto.

Come conseguenze:

  • L'operando di sizeof può essere un tipo tra parentesi sizeof (int), invece di un'espressione di oggetto.
  • Le parentesi non sono necessarie: int a; printf("%d\n", sizeof a);va benissimo. Sono spesso visti, in primo luogo perché sono necessari come parte di un'espressione cast di tipo, e in secondo luogo perché sizeof ha una precedenza molto alta, quindi sizeof a + bnon è la stessa di sizeof (a+b). Ma non fanno parte dell'invocazione di sizeof, sono parte dell'operando.
  • Non puoi prendere l'indirizzo di sizeof.
  • L'espressione che è l'operando di sizeof non viene valutata in fase di esecuzione ( sizeof a++non modifica a).
  • L'espressione che è l'operando di sizeof può avere qualsiasi tipo eccetto void o tipi di funzione. In effetti, questo è un po 'il punto di sizeof.

Una funzione sarebbe diversa su tutti questi punti. Ci sono probabilmente altre differenze tra una funzione e un operatore unario, ma penso che sia sufficiente per mostrare perché sizeof non potrebbe essere una funzione anche se ci fosse un motivo per volerlo.


3
Wow, proprio quello che stavo pensando!
crashmstr

7
Non posso dirlo meglio.
Clement Herreman,

Credo che al giorno d'oggi le cose siano più complesse a causa degli array a lunghezza variabile (VLA). IIRC, lo standard consentirebbe anche sizeofdi avere effetti collaterali se c'è un VLA nell'espressione.
Aaron McDaid

@glglgl No, non ha alcun senso. In quel contesto, (int)non è niente di speciale - solo un nome di un tipo tra parentesi. Le parentesi qui fanno parte della sintassi di sizeof: sono richieste quando si prende la dimensione di un tipo, ma non sono richieste quando si prende la dimensione di un'espressione. Vedi ad esempio qui
anatolyg

1
Lo standard utilizza due notazioni per sizeof: sizeof unary-expressione sizeof ( type-name )- quindi nello standard C11 non è considerato un "cast" ma un nome di tipo tra parentesi. Il risultato netto è più o meno lo stesso. (Per confronto, un'espressione cast è ( type-name ) cast-expression.) E odio il modo in cui il commento Markdown funziona diversamente da Q&A Markdown!
Jonathan Leffler

24

Può essere utilizzato come costante del tempo di compilazione, il che è possibile solo se è un operatore piuttosto che una funzione. Per esempio:

union foo {
    int i;
    char c[sizeof(int)];
};

Sintatticamente, se non fosse un operatore, dovrebbe essere una macro del preprocessore poiché le funzioni non possono accettare tipi come argomenti. Sarebbe una macro difficile da implementare poiché sizeofpuò prendere come argomento sia i tipi che le variabili.


4
+1 ma si noti che non è una costante del tempo di compilazione quando l'argomento è un VLA - array a lunghezza variabile.
Jonathan Leffler

6

Perché lo standard C lo dice e ottiene l'unico voto.

E lo standard è probabilmente corretto perché sizeofaccetta un tipo e

In generale, se il dominio o il codominio (o entrambi) di una funzione contiene elementi significativamente più complessi dei numeri reali, quella funzione viene chiamata operatore. Al contrario, se né il dominio né il codominio di una funzione contengono elementi più complicati dei numeri reali, è probabile che quella funzione venga chiamata semplicemente una funzione. Le funzioni trigonometriche come il coseno sono esempi di quest'ultimo caso.

Inoltre, quando le funzioni vengono utilizzate così spesso che si sono evolute in notazioni più veloci o più facili rispetto alla forma generica F (x, y, z, ...), le forme speciali risultanti sono anche chiamate operatori. Gli esempi includono operatori infisso come addizione "+" e divisione "/" e operatori suffisso come fattoriale "!". Questo utilizzo non è correlato alla complessità delle entità coinvolte.

(Wikipedia)


Questo probabilmente spiega la motivazione dello standard C (e di altri linguaggi di programmazione) nell'usare i termini "operatore" e "funzione" come fanno.
Steve Jessop,

5

Perché non è una funzione. Puoi usarlo in questo modo:

int a;
printf("%d\n", sizeof a);

La funzione ha un punto di ingresso, codice, ecc. La funzione deve essere eseguita in fase di esecuzione (o inline), la dimensione di deve essere determinata in fase di compilazione.


2

L'operatore sizeof è un'entità in fase di compilazione non runtime e non necessita di parentesi come una funzione. Quando il codice viene compilato, sostituisce il valore con la dimensione di quella variabile in fase di compilazione, ma in funzione dopo che la funzione viene eseguita, conosceremo il valore restituito.


1

Perché:

  • quando si passa un valore a una funzione, la dimensione dell'oggetto non viene passata alla funzione, quindi una sizeof"funzione" non avrebbe modo di determinare la dimensione
  • in C, le funzioni possono accettare solo un tipo di argomento; sizeof () deve accettare tutti i tipi di cose diverse (variabili così come tipi! Non puoi passare un tipo a una funzione in C)
  • la chiamata a una funzione implica la creazione di una copia degli argomenti e altri sovraccarichi non necessari

1

C'è una piccola differenza dalla funzione: il valore di sizeof viene risolto in fase di compilazione, ma non in fase di runtime!


7
Ad eccezione di VLA - array di lunghezza variabile - argomenti.
Jonathan Leffler

1

Perché è un operatore in fase di compilazione che, per calcolare la dimensione di un oggetto, richiede informazioni sul tipo che sono disponibili solo in fase di compilazione. Questo non vale per C ++.


0

sizeof()L'operatore è un tempo di compilazione sarebbe occorrenza. Può essere utilizzato per determinare i parametri o gli argomenti.


-1

Sizeof (), penso che ovviamente sia sia una funzione che un operatore. Perché? Perché una funzione contiene le parentesi per l'ingresso nella fase di ingresso. Ma principalmente anche un operatore causa operatori sono caratteri di azione, quindi sizeof è un'istruzione di azione che agisce sull'operando tra parentesi.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.