Что означает имя типа в скобках перед переменной? - PullRequest
1 голос
/ 06 июня 2011

У меня возникли проблемы с пониманием этого куска кода. Это из книги, которую я читаю, но я чувствую, что парень просто говорит мне набирать тексты без подробного объяснения.

- (IBAction)sliderChanged:(id)sender
{
    UISlider *slider = (UISlider *)sender; //set slidervar as active slider
    int progressAsInt = (int)(slider.value + 0.5f);
    NSString newText = [[NSString alloc] initWithFormat:@"%d",progressAsInt];
    sliderLabel.text = newText;
    [newText release];
}

проблема с первой строкой

UISlider *slider = (UISlider *)sender; //set slidervar as active slider

Я не понимаю, что такое типизация, о чем говорит парень в книге. «Избегает необходимости отправлять отправителя каждый раз, когда мы его используем»

Я также не понимаю, что / почему вторая строка содержит int в скобках. Я привык иметь код вроде

int progressAsInt = 56

Ответы [ 3 ]

2 голосов
/ 06 июня 2011

Typecasting - это метод сообщения компилятору о том, что тип отличается от того, что есть.Он вовлечен в обе части вашего вопроса.Вы применяете что-то, помещая новый тип в скобки перед элементом, который вы кастуете.

UISlider *slider = (UISlider *)sender;

Когда метод объявлен, sender имеет тип id.Поскольку вы знаете, что это должен быть слайдер, вы приводите его к UISlider * и сохраняете его в переменной с таким типом, чтобы компилятор не выдавал вам предупреждения при попытке использовать специфические свойства слайдера.

int progressAsInt = (int)(slider.value + 0.5f);

Здесь slider.value - число с плавающей запятой.Так как вы хотите сохранить его в целочисленном типе, вам нужно привести его в соответствие.Когда значение типа float приводится к int, оно автоматически округляется до нуля.Код хотел, чтобы он был округлен до ближайшего целого числа, поэтому он добавил 0,5 перед приведением.

2 голосов
/ 06 июня 2011

Ваша проблема в том, что вы не понимаете C. Objective-C - это тонкий слой над C, который добавляет классы и обмен сообщениями.Проверьте хорошую книгу C, например одну из "The Definitive C Book Guide и List" .

Без получения ссылки на объект, который напечатан как UISlider *, вы быневозможно использовать синтаксис свойства без, в каждом случае, приведения ссылки sender к нужному типу, например, ((UISlider *)sender).value.Даже если вы не использовали нотацию с точкой свойства, приведение также было бы необходимо, чтобы компилятор обрабатывал [slider value] как возвращающий что-то отличное от id.

Книга просто глупа,хоть.Нет требования, чтобы аргумент метода действия был напечатан как id.Когда вы знаете, что отправитель всегда будет определенного типа - как в этом случае, когда код предполагает, что sender всегда будет своего рода UISlider - вы можете просто использовать этот тип в методеобъявление:

- (IBAction)sliderChanged:(UISlider *)sender
{
    /* code */
}

Это лучше документирует намерение программиста - документацию, которую собирает Interface Builder, - а также полностью исключает необходимость выполнения приведения в методе.

В общем,если вам нужно выполнить Typecast, есть большая вероятность, что вы делаете что-то не так.

В качестве другого примера, давайте посмотрим на эту строку:

int progressAsInt = (int)(slider.value + 0.5f);

Здесь явный int typecastне нужноПоскольку присваивание имеет значение int l, значение с плавающей запятой, возникающее в результате сложения, обязательно будет приведено к int как часть присваивания.

1 голос
/ 06 июня 2011

По сути, компьютер (на самом деле компилятор, но мы можем притворяться ради простоты) знает только то, на что вы ссылаетесь, из-за его «типа».Типом может быть int, or UISlider * `или любое количество других вещей.Это классификация для переменной.

Вверху вы можете видеть, что sender имеет тип id, что означает, что компьютер не знает, что это за объект.

Когда вызывается этот метод, вы получаете объект, который называется sender.Но даже если вы знаете, что отправитель UISlider*, вы не можете вызывать методы UISlider для него, потому что компьютер этого не знает.

Когда вы говорите UISlider *slider = (UISlider *)sender;, вы говорите: «Эй, компьютер, я говорю тебе, что отправителем является UISlider *, и с этого момента я буду называть его slider. Вот что такое типизация.

То же самое касается int progressAsInt = (int)(slider.value + 0.5f);

(slider.value + 0.5f) на самом деле float, который похож на число с десятичными числами. Вы не можете просто присвоить число с плавающей запятой, предназначенное для int с, поэтомувместо этого вы говорите «Пожалуйста, превратите этот float в int для меня», поставив (int) впереди.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...