Hvad er en statisk funktion i C?

Bedste svar

Da vi ved, at de funktioner, der er defineret i en fil, kan fås i en anden fil. Hvis vi vil begrænse, at funktioner ikke skal kaldes i en anden fil, kan vi gøre dem statiske.

Derfor er statiske funktioner de funktioner, der kan kaldes i den samme fil, hvor de definerer .

Vi kan definere en funktion statisk ved hjælp af følgende syntaks

static return\_type function\_name(arguments)

{

function\_body;

}

Her er en funktion til at finde kvadratroden af ​​et givet nummer

static long int getSquare(int num){

return (num*num);

}

Program til demonstration af eksempel på statisk funktion i C-sprog

#include

//static function definition

static long int getSquare(int num){

return (num*num);

}

int main()

{

int num;

printf("Enter an integer number: ");

scanf("\%d",&num);

printf("Square of \%d is \%ld.\n",num,getSquare(num));

return 0;

}

Output

Enter an integer number: 36

Square of 36 is 1296.

Hvorfor er de statiske funktioner påkrævet?

Da funktioner bruges til at genbruge koden (dvs. den kode, du har skrevet, kan få adgang til i en anden fil ved at placere dem i funktionerne ), men når du vil definere noget funktioner, der ikke skal kunne deles (kan kaldes) i en anden fil .

statiske funktioner er også nyttige til at håndtere problem med erklæringskonflikt – hvis der er to funktioner i to forskellige filer med samme navn, er funktionserklæringen i konflikt. Vi kan gøre dem statiske.

For at opfylde en sådan type krav kan vi gøre dem statiske .

Svar

Kort svar: Det betyder, at funktionsnavnet kun er synligt og kan kaldes i den fil, der aktuelt kompileres. Andre filer, der er kompileret separat, kan ikke se funktionsnavnet eller kunne kalde det. Derefter kan de have deres egne statiske funktioner med samme navn. Dette undgår navnekollisioner i filindeslutninger og ved sammenkædning af objektfiler og binære biblioteker.

Der er 4 forskellige lagringsklasser til lagring i C.

  • auto (automatisk) dette er “almindeligt” (standard) og bruger nøgleordet auto , men er normalt ikke angivet, da det er standard
  • register er et “tip” til compileren, at det muligvis optimerer den oprettede kode for at gemme værdi i et cpu-register til hurtigere behandling. Compileren vil prøve, hvis den kan gøre det, men hvis ikke, er det det samme som almindeligt.
  • eksternt eksternt betyder, at der er kun en global variabel med det navn, og alle filer, der erklærer den som ekstern, bruger den lagring. En fil erklærer den globalt som en almindelig variabel, hvor den tildeles ved kompilering.
  • statisk lagringsspecifikator i C-kildefiler betyder et par forskellige ting.

  1. Navnet og lageret eksporteres ikke til andre filer, der kompileres på samme tid. Dette gør det muligt for hver fil at have identiske navne, der ikke kolliderer.
  2. Det lager, der oprettes for variablen, oprettes i det statiske lagerområde og initialiseres til 0 ved programstart eller med en eksplicit værdi.
  3. Initialisering af en statisk variabel udføres kun en gang . (ved samlingstidspunktet). Derefter holdes de tildelte værdier i programmets levetid, eller indtil de ændres af en opgave.
  4. Statisk lagring, der er erklæret inde i funktioner, har funktionsomfang, men statisk tildeling. Dette betyder, at lagringen er permanent i programmets levetid og ikke oprettes, når funktionsstakrammen er allokeret til funktionsopkaldet. Det bevarer sin værdi gennem flere funktionsopkald. Lagringen fortsætter, selvom kodeblokken gendannes fra stakken, når den vender tilbage.

int accumulate( unsigned int x)

{

static unsigned int acc = 0;

acc = acc + x;

return acc;

}

  1. Ovenstående ville vende tilbage en løbende opgørelse af dens input, da var acc ville beholde værdien gennem hvert opkald. acc initialiseres til 0 ved programindlæsning.
  2. statiske variabler har adresser i RAM, og du kan sende dem til funktioner ved hjælp af reference eller værdi.
  3. Variabler med mindre omfang (defineret inden i funktioner), der har samme navn som en statisk variabel uden for dette omfang, skygger den statiske variabel, som alle andre.
  4. statiske variabler er muligvis ikke eksporteret til eksterne filer, så værdier kan gå tabt på tværs af kompileringsdomæner, hvis de ikke udtrykkeligt sendes som parametre efter værdi. (gotcha!)
  5. Som 4 kan andre filer ikke få adgang til statiske variabler som extern som de kunne med automatiske (normale) variabler. Det fungerer ikke, du får buggy-programmer, der går ned, og compileren kan blive narret og gå glip af det.
  6. Statiske variabler kan initialiseres ved deres erklæring, men initialiseringsværdien skal være et konstant udtryk, evaluerbart ved kompileringstid, ikke en værdi, der ikke kan beregnes på kompileringstidspunkt. Du kan ikke initialisere en statisk variabel med en ukendt værdi, såsom en parametervariabel, eller resultatet af et funktionsopkald, der ikke er fundet på kompileringstidspunktet.

int accumulate( unsigned int x)

{

/* ERROR x is not a compile-time constant. */

static unsigned int acc = x;

static unsigned int acc = 0; /* OK */

acc = acc + x;

return acc;

}

Statiske funktioner

  1. En statisk funktion i C har filomfang . En statisk funktion kan ikke være kaldes af en anden fil i samme oversættelsesenhed. En oversættelsesenhed er al kildekode, der går ind i en kompilator efter forbehandling, der skal kompileres ad gangen. Statiske funktioner har ikke adgang til statiske variabler eller kalder statiske funktioner fra andre filer. Så hvis du vil begrænse adgangen til en funktion til den aktuelle fil, kan du gøre den statisk. Kun en funktion ved det navn kan eksistere i den fil (som også gælder for almindelige funktioner), så ofte placeres hjælpefunktioner i headerfiler, der skal inkluderes i flere kompileringer, og headeren beskyttes med præprocessorkommandoer for ikke at være inkluderet i enhver kompilationsenhed mere end én gang. Alle standard C-biblioteksoverskrifter er fulde af globale funktioner, og de er beskyttet, så de kun kompileres en gang i en samling og er globale funktioner. Ingen statiske funktioner. Statiske funktioner siges at have ‘intern sammenkædning’ hvilket betyder, at de ikke kan ses i andre kompilerede moduler, selvom de er knyttet til det samme endelige program eller bibliotek. Hvis en funktion ikke er statisk , er denne funktion i C en global funktion og vil være tilgængelig i hele programmet globalt. Dette betyder, at du kun kunne have en funktion kaldet print i hele programmet . For at omgå dette skal du gøre dine funktioner og variabler statiske, så får du ikke et sammenstød med navne.
  2. Funktioner er globale og eksterne som standard undtagen i filen, de er defineret i. Så du kan ikke se ordet extern bruges i C-kilde med funktioner, fordi det allerede er der implicit. Dette er grunden til, at du kan kalde normale funktioner fra enhver fil i oversættelsesenheden. De siges at have ekstern sammenkædning , hvilket betyder, når de først er linket ind, de er synlige og kan kaldes af enhver fil i modulet eller ethvert andet modul i det sammenkædede program.
  3. En funktionsprototypedeklaration er en “foreløbig definition”, der er implicit ekstern . Kode efter prototypedeklarationen er scannet for første gang kan kalde funktionen, så længe den fulde definition findes i den endelige kode. Det betyder, at en “faktisk definition” faktisk skal eksistere, ellers linkingsfasen mislykkes. Dette er grunden til, at overskrifter i C normalt ikke indeholder kildekoden til funktionerne, de er ikke nødvendige for at kompilere, men er i sammenkædningsfasen.
  4. En prototype-erklæring om statisk funktion er en “foreløbig definition”, der eksplicit ikke er ekstern . Den fulde definition skal være til stede i den aktuelle oversættelsesenhed (kompileret på samme tid), ellers kompileringen mislykkes. Moderne C-compilere syntetiserer prototypen ud fra definitionen, så længe den forekommer tidligere end et faktisk funktionsopkald. Såkaldte “forward declarations” tillader brug af foreløbige definitioner med den aktuelle definition senere og har forskellige anvendelser i datastrukturer og i organiseringen af ​​biblioteker.
  5. Den første definition af en filsignatur er den, der bruges til hele programmet, inklusive statisk eller ekstern. Når en funktion først er defineret, hvis den oprindeligt erklæres som statisk, vil den altid være statisk, selvom den omdefineres senere uden det statiske nøgleord. Hvis der oprindeligt erklæres ekstern (standard), kan den ikke omdefineres som statisk.

static void f(int); /* Function is always static */

...

void f(int x) { ….} /* static , not exported, no error */

void f(int); /* Function is always global */

...

static void f(int x) { ….} /*ERROR NOT STATIC */

clang: "error: static declaration of "f" follows non-static declaration"

  1. Funktioner defineret i blokområdet kan ikke erklæres statisk. Kun definitioner af statiske funktionsomfang kan foretages uden for enhver blok. Dette giver mening fra et logisk perspektiv, da filomfang ikke kan gøres mindre end hele filen. Så definer en statisk funktion eller i det mindste prototypen meget tidligt i filen.
  2. Statisk henviser til funktionen, ikke returtypen . Du kan placere det statiske nøgleord efter returtypen, hvis du ønsker det, men hvis du gør det, er du underlig, og du vil forvirre folk. Returnværdien er ikke statisk, funktionen er.
  3. En definition af statisk funktion tilsidesætter ikke en global defineret før den i den samme fil eller i en inkluderet fil. Hvis der allerede er defineret en funktion med det navn, kan du ikke omdefinere den med en statisk funktion eller nogen samme navnefunktion.

C omdøber ikke funktioner og variabler internt som C ++ gør, så det understøtter ikke overbelastning af funktioner. C ++ “mangler” funktionsnavne med et kodet navn, der angiver flere ekstra slags data, f.eks. Hvis det er en del af en klasse, eller hvad dens parametre er osv. Så i C fraværende det statiske nøgleord har du muligvis kun en funktion af hvert unikke navn i et program, uanset hvor mange filer eller biblioteker det medfører.

Så hvad gør du, hvis du vil ændre din funktion til en allerede eksisterende tidligere?

Nå, hvad smarte C-kodere gør, er at komme med et andet navn til deres funktion. Men der er en måde at narre kompilatoren ved forebyggende at ændre kildeteksten med forprocessoren.

Eksempel: En eller anden idiot skrev en int sort( char** Array) -funktion i sit bibliotek og gjorde det globalt, og det er buggy og gør ikke nøjagtigt, hvad du vil, fordi det får tal til at komme efter bogstaver eller noget, og T-ordene er altid først af en eller anden grund.

Du vil brug biblioteket, men har brug for at rette funktionen, og du har kun overskrifterne og det kompilerede bibliotek, ikke kildekoden.

OK> så der oprettes en “speciel” overskrift, der erstatter al forekomst af ” sorter “med” dårlig\_sort “i overskriften, importerer derefter din kode og erstatter alle forekomster af” sorter “med” god\_sort “. “Good\_sort” er defineret fuldstændigt i good\_sort.h, men er markeret statisk, så det er kun kendt i filen, det er inkluderet i.

/* good\_sort.h */

#ifndef \_GOOD\_SORT\_H

#define \_GOOD\_SORT\_H

static int good\_sort(char** Array)

{

... //code here

return numsorted;

}

#endif

Der tilføjes en definitionsbeslag for at sikre, at den ikke er inkluderet to gange.

/*-----------------------------------*/

/* program.c */

#include "Trumpsort.h" /* The buggy library header */

...

#ifdef sort

#undef sort /* undefine the sort function name as reserved */

#define sort bad\_sort /* replace the name */

#include "good\_sort.h" /* your fixed version */

#endif

#define sort good\_sort /* replace the name in this file */

/* rest of file */

Lidt af en crapfest, men ideen er at kalde din funktion i stedet for den dårlige ved omdøbning ing det til “good\_sort” og kalder det i stedet. (men kun i denne fil – statisk ).

Skriv et svar

Din e-mailadresse vil ikke blive publiceret. Krævede felter er markeret med *