Главная » iPhone, Objective-C, Программирование для iOS и MacOS » Программирование функций с передачей аргументов по ссылке Objective-C

0

Положение точки на плоскости обычно определяется в одной из двух систем координат: декартовой или полярной. В декартовых координатах запись (х,у) обозначает смещение вправо на х и вверх на у от начала координат. В полярных координатах запись (theta, radius) обозначает поворот влево на theta радиан со смещением на расстояние radius от начала координат.

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

Рис. 9.2, Полярные и декартовы координаты

Объявление функции выглядит примерно так:

void cartesianTоPolar(float х, float у, float *rPtr, float *thetaPtr)

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

radius и theta.

Включите функцию преобразования в начало файла main.c и вызовите ее из

main():

#include <stdio.h>

#include <math.h>

void cartesianToPolar(float х, float у, dоublе *rPtr, dоublе *thetaptr)

{

// радиус сохраняется по переданному адресу

*rPtr =sqrt(x *х+у*у);

// вычисление theta; float theta;

if (х ==0.0) {

if (у ==0.0) {

theta = 0.0; // формально неопределенное значение

}else if (у>0){

theta =МРI 2;

}else{

theta = -­‐ M_PI_2;

}

}else{

theta = atan(y/x);

}

// значение theta сохраняется по переданному значению

*thetaPtr = theta;

}

int main(int argc, const char * argv[])

{

dоublе pi = 3.14; dоublе integerPart; dоublе fractionPart;

// адрес integerPart передается в аргументе fractionPart = modf(pi, &integerPart);

// определение значения, сохраненного integerPart

printf("integerPart = %.0f, fractionPart = %.2f\n", integerPart, fractionPart);

dоublе х = З.О; dоublе у =4.0; dоublе radius; dоublе angle;

cartesianToPolar(x, y, &radius, &angle);

printf("(%.2f, %.2f) becomes (%.2f radians. %.2f)\n", х, у. radius. angle);

return 0;

}

Постройте и запустите программу.

Рис. 9.3. Состояние стека при возврате из cartesianToPolar()

Избегайте разыменования NULL

Иногда функция может получать по ссылке сразу несколько значений, тогда как вас интересует только часть из них. Как избежать объявления всех переменных и передачи их адресов, которые все равно не будут использоваться? Обычно вы передаете вместо адреса NULL, говоря тем самым функции: «Это конкретное значение мне не понадобится».

Но это означает, что перед разыменованием каждого указателя всегда следует

убеждаться в том, что он не равен NULL. Включите в функцию cartesianToPolar()

следующие  проверки:

void cartesianToPolar(float x, float y, double *rPtr, double *thetaPtr)

{

// Указатель rPtr отличен от NULL? if (rPtr) {

// Радиус сохроняется по переданному адресу

*rPtr = sqrt(x * x + y * y);

}

// Указатель thetaPtr равен NULL? if (!thetaPtr) {

// Пропускаем остаток функции

return;

}

// Calculate theta float theta;

if (x == 0.0) {

if (y == 0.0) {

theta = 0.0;

} else if (y > 0) { theta = M_PI_2;

// формально неопределенное значение

} else {

theta = -­‐ M_PI_2;

}

} else {

Источник: Аарон Хилегас, «Objective-C. Программирование для iOS и MacOS», 2012 г.

По теме:

  • Комментарии