Жергілікті көлем мен функция ауқымы арасындағы айырмашылық

Мен осы екі мағынаны бірдей деп ойлағаннан кейін, бірақ бұл туралы көбірек оқығаннан кейін, мен әлі айырмашылығын білмеймін. Жергілікті қамту кейде функция ауқымына жатпайды ма? және бұл тек жапсырмалардың функционалдық ауқымы бар дегенді білдіреді?

4
кейде «жергілікті ауқым» деп аталады, кейде C ++ 03-те «блоктық аумақ» деп аталады, енді C ++ 11-де барлық жерде «блоктық аумақ» деп аталады. Шиеленістердің бір көзі аз!
қосылды автор Johannes Schaub - litb, көзі

5 жауаптар

void doSomething()
{                                    <-------
     {                   <----               | 
                              |              |
         int a;           Local Scope    Function Scope
                              |              |
     }                   <----               | 
}                                    <------- 

Функция ауқымы сыртқы { } арасында.

Local scope is between inner { }

{``} арқылы жасалған кез-келген ауқым функцияның басында {``} функциясының масштабын жасаған кезде жергілікті ауқым деп атауға болады.
Мәселен, кейде Жергілікті қамту Scope функциясымен бірдей болуы мүмкін.

бұл тек жапсырмалардың функционалдық ауқымы бар дегенді білдіреді?

Labels are nothing but identifiers followed by a colon. Labeled statements are used as targets for goto statements. Labels can be used anywhere in the function in which they appear, but cannot be referenced outside the function body. Hence they are said to have Function Scope.

Код мысалы:

int doSomething(int x, int y, int z)
{
     label:  x += (y + z);   /*  label has function scope*/
     if (x > 1) 
         goto label;
}

int doSomethingMore(int a, int b, int c)
{
     if (a > 1) 
         goto label; /*  illegal jump to undefined label */
}
15
қосылды

Жергілікті аумақ - бұл {және оның жабылуы) арасындағы аймақ. Функция көлемі - «жергілікті» кеңістіктерді қамтуы мүмкін функцияны ашу мен жабу арасындағы аймақ. Белгі ол анықталған функцияның толықтай көрінеді, мысалы:

int f( int a ) 
{
    int b = 8;
    if ( a > 14 )
    {
       int c = 50;
       label:
       return c - a - b;
    }
    if ( a > 7 ) goto label;
    return -99;
}

int c is not visible outside its enclosing block. label is visible outside its enclosing block, but only to function scope.

4
қосылды
Жоқ, @Rob, егер тілде жергілікті емес годарлар болса, тек бір функциядан екіншісіне секіре аласыз. Бірақ, олар міндетті түрде пакеттік мәміле болып табылмайды. Ғаламдық жапсырма атаулары бар жергілікті ғана готара тек сіздің этикеткаларыңыздың атауларын таңдағанда абай болу керек, сондықтан олар протекторлық макростар үшін аттарды таңдағанда, бағдарламаның кез келген жерінде этикеткалармен араласпайды.
қосылды автор Rob Kennedy, көзі
Мен әрдайым жапсырмалардың жаһандық ауқымы бар деп ойладым. Функция көлемі әлдеқайда ақылға қонымды.
қосылды автор deft_code, көзі
Егер жапсырмалардың жаһандық ауқымы болса, сіз бір функцияның денесінен басқа адамның денесіне секіре аласыз.
қосылды автор Rob K, көзі
Жақсы түсініктеме. Жаһандық ауқым/шынымен/этикеткалар аттары жергілікті емес гооспен бірге жүрместен ешқандай мағына бермейді. Сіз айтып кеткендей, бұл аттар кеңістігінің ластануы ғана еді.
қосылды автор Rob K, көзі

Жергілікті қамту кейде функция ауқымына жатпайды ма?

Ия. C тілінен алынған көптеген тілдерде айнымалылар жарияланған аумақта жарамды. Егер сіз функцияның ішіндегі айнымалы мәнді жарияласаңыз, бірақ кез-келген басқа код блогында емес, онда бұл айнымалылар әдетте «жергілікті» немесе «автоматты» айнымалы деп аталады. Функцияның кез келген жеріне сілтеме жасай аласыз. Екінші жағынан, егер айнымалы мәнді басқа код блок ішіне жарияласаңыз - мысалы, шартты мәлімдеме корпусында, айнымалы мән осы блоктың ішінде ғана жарамды. Мұнда бірнеше басқа жауаптар жақсы мысалдар келтіреді.

және тек жапсырмалардың функционалдық ауқымы бар деген не?

деген не?

Мәтінмән пайдалы болар еді, бірақ бұл функциядан бір функциядан басқа функцияға өту мүмкін емес дегенді білдіреді.

void foo(int a) {
    if (a == 0) goto here; //okay -- 'here' is inside this function
    printf("a is not zero\n");
    goto there;            //not okay -- 'there' is not inside this function
here:
    return;
}

void bar(int b) {
    if (b == 0) goto there;//okay -- 'there' is in this function
    printf("b is not zero\n");
there:
    return;
}

Шошқаның ұясын қоздырмау керек, бірақ жапсырмалардың көлемі тым жиі пайда болмайды. Жапсырмалар негізінен goto сөзімен пайдалы, ол өте сирек жағдайда қажет болса, тіпті егер сіз goto пайдалануды таңдасаңыз да, мүмкін, тіпті ойлауға болмайды басқа функцияға өту үшін.

2
қосылды
Қалай тән, C-дің жергілікті қамтуы жоқ, жай AFAIK функциясы.
қосылды автор Mooing Duck, көзі

Функцияның ауқымы body функциясының ауқымынан сәл үлкенірек: функция дәлелдері сыртқы аумақта, ал жергілікті айнымалы мәндер тек ішкі ішінде болады. Бұл функция-try-block ішіндегі ең айқын көрінеді:

void f(int a) try {
 //function body
} catch(...) {
 //catch block
}

Аулауға арналған блокта тек функционалдық ауқымда айнымалылар ғана емес, сонымен қатар жергілікті айнымалылар емес.

Әрине, әрі қарай тереңірек кірістірілген аумақтарды енгізе аласыз және жасай аласыз, мысалы: for үшін циклдық органдар немесе шартты органдар.

1
қосылды
@Downvoter, қарсылықты түсіндіруге қам жасайсыз ба?
қосылды автор Kerrek SB, көзі
@Caleb: Бұл конструктор үшін қолданғаныңызды елестетіңіз ... содан кейін оны кез-келген уақытта пайдаланып көріңіз :-)
қосылды автор Kerrek SB, көзі
@Caleb: Сіз бұл қарауыңызға болады.
қосылды автор Alok Save, көзі
+1 Мен бұрын C ++-ді көп жаздым, бірақ мен оны ешқашан көрген емеспін.
қосылды автор Caleb, көзі
@KerrekSB: Бұл мені тағы неге жіберіп алар еді деп сұрайды, бірақ мен шынымен білгім келетініне сенімді емеспін.
қосылды автор Caleb, көзі
bool m[3][3];
void f1()
{
  int i;
 //redefining a variable with the same name in the same scope isn't possible
  //int i; //error C2086: 'int i' : redefinition
}

void f2()
{
  int i;//ok, same name as the i in f1(), different function scope.

  {
    int i;//ok, same name as the i above, but different local scope.
  }

 //the scope if the following i is local to the for loop, so it's ok, too.
  for (int i = 0; i < 3; i++)
  {
    for (int j = 0; j < 3; j++)
    {
      if (m[i][j])
        goto loopExit;
    }
  }
loopExit:
  std::cout << "done checking m";
// redefining a label with the same name in the same function isn't possible
// loopExit:;//error C2045: 'loopExit' : label redefined
}

void f3()
{
loopExit:;//ok, same label name as in f2(), but different function scope
}
1
қосылды