2015-06-10 3 views
8

Это мой код:Сфера имени переменной и функции

#include <stdlib.h> 
#include <stdio.h> 

int sum(int,int); 

int sum(int x, int size) { 
    int sum = 0; 
    printf("%p\n", &x); 
    printf("%p\n", &size); 
    printf("%p\n", &sum); 
    sum(x,size); 
    return 0; 
} 

int main() { 
    sum(2,4); 
    return 0; 
} 

И ошибка я получаю:

hello.c:11:5: error: called object type 'int' is not a function or function pointer 
sum(x,size); 
~~~^ 
+12

Вы действительно хотите, чтобы переменная и функция имели одно и то же имя? –

+0

@SouravGhosh Почему это проблема? –

+5

И вообще, как вы думаете, что вы делаете при вызове 'sum (x, size);'? Нет ничего, что бы остановить рекурсию, поэтому ваша программа будет проходить цикл в течение всего дня (по крайней мере, до тех пор, пока она не достигнет максимального стека). – Eregrith

ответ

11

Если определить две отдельные идентификаторов таким же имя для различных объектов в том же пространстве имен, они могут перекрывать друг друг. C11 стандарт, глава §6.2.1 состояния,

Если идентификатор обозначает две разные сущности в одноименной пространстве, прицелы может перекрываться ....

См Сноска: Почему в этот сценарий, как sum s в том же пространстве имен

Итак, когда вы повторно определить идентификатор с каким-либо другим типом,

.... Если да, то объем одного лица (внутренней области видимости) закончится строго до объема другого лица (внешней области). Внутри внутренней области идентификатор обозначает объект, объявленный во внутренней области; объект, объявленный во внешней области, равен , скрытый (и не отображается) во внутренней области.

Это означает, что, по существу, в вашем случае, внутри функции sum(), когда вы определяете int sum, в основном вы затенения функциюsum. После переопределения sum является идентификатором типа int, в котором область действия. Таким образом, внутри функции sum() вы не можете позвонить по телефону sum(), так как это тип int.

Однако FWIW, вызов sum() в main() (или, скорее, за пределами самого sum()) должен быть действительным, так как в этой точке, int sum будет вне сферы.

Изменить имя переменной int sum на что-то другое.

Благодаря @pmg для коррекции

EDIT:

Как уже упоминалось in the other answer by @juanchopanza, после изменения затенения имени переменного, ваша программа будет собирать и как только вы запустите его, вы» ll face infinite recursion из-за безусловный звонок в sum() внутри sum() сам. Вам нужно добавить перерыв состояние до конца (return от) рекурсия.


Сноска:

Ссылаясь на C11, глава §6.2.3, пространства имен, можно сказать, есть отдельные пространства имен для различных категорий идентификаторов, например 1) имена ярлыков 2) теги структур, союзов и перечислений, 3) члены структур или союзов и 4) все остальные идентификаторы.

Таким образом, в данном конкретном случае, функция sum() и int sum определение будет находиться в том же пространстве имен, для sum() области видимости функции в

+0

Я согласен, как только смогу. Спасибо за указатель. –

+0

Да, вы можете иметь одинаковый идентификатор для разных вещей ... в разное время. – pmg

+0

@SouravGhosh. Существуют вездеводные вездеходы. –

12

Вы изменили значение sum здесь:

int sum = 0; 

Отныне, в области, в которой он был объявлен, sum является int, и это становится бессмыслицей:

sum(x,size); /* Wat? sum is an int!!! */ 

Не делайте этого, и ваш код будет скомпилирован. Как только он скомпилируется, вы можете беспокоиться о прекращении рекурсии.

4

Вам нужно изменить int sum = 0 к int y = 0, и вашей программе будет перерыв, как вы не остановить рекурсию на sum(x,sum)

6

Область имеет значение

  1. Название функции sum здесь есть глобальный охват.
  2. Переменная sum является местной и имеет местный охват.

  3. Конфликт в том, что внутри sum() вы звоните sum(). Теперь внутри функции sum() у вас есть 2 объекта одинакового имени и другого типа, поэтому ошибка.

Если у вас что-то вроде

int sum() 
{ 
    int sum = 0; 
    sum = 10; 
    printf("%d\n",sum); 
} 

Тогда ваш код был бы в порядке. Поскольку переменная sum является локальной для функции sum(), и это единственный объект внутри функции sum() с этим именем.

Вместо того, чтобы беспокоиться об этом лучше переименовать переменную и убедитесь, что имя переменной и имя функции отличается

2

Просто измените переменную сумма имя внутри функции сумма в общей

#include <stdlib.h> 
#include <stdio.h> 

int sum(int,int); 

int sum(int x, int size) { 
    int total = 0; 
    printf("%p\n", &x); 
    printf("%p\n", &size); 
    printf("%p\n", &total); 
    sum(x,size); 
    return 0; 
} 

int main() { 
    sum(2,4); 
    return 0; 
} 
1

Переменная и функция имеют одно и то же имя, поэтому функция де-ссылки и переменная одинаковы, то есть причина ошибки

Смежные вопросы