Этот раздел посвящен
Пусть у нас есть некоторая кривая, и мы хотим построить ее изображение на растровой решетке. Возникает вопрос: какие из ближайших пикселей следует закрашивать? В данной и следующей лекциях мы рассмотрим случай построения на монохромном растре, когда возможны только два уровня интенсивности закраски пикселя - "полностью закрашен" или "полностью не закрашен". Если же допустимы несколько уровней интенсивности, то можно растеризовывать более аккуратно, уменьшая эффекты алиасинга (т.е. ступенчатости), см. раздел 7.2.
(рис 3.1) Изображение кривых на растре.Пусть (x0, y0) - фиксированный пиксель, а (x, y) - некоторый другой пиксель на плоскости. Тогда для определения их близости вводятся следующие понятия:
1. 4-связность|x-x0|+|y-y0|=1 |
![]() |
2. 8-связностьmax{|x-x0|, |y-y0|}=1
|
![]() |
В дальнейших рассуждениях расстояние будем считать заданным стандартной евклидовой dist(P1,P2) = ((x1 - x2)2 + (y1 - y2)2)1/2
Пусть наш отрезок - это AB. Перейдем от системы координат Oxy к Ax'y' (см. рис. 3.2, этап 1). Отрезок может лежать в любом из 8 октантов, но всегда существуют симметрии относительно осей,
разделяющих эти октанты, симметрии определяются матрицами$$\left( \begin{array}{cc}
\pm 1 0 \\
0 \pm 1
\end{array} \right)$$
и$$\left( \begin{array}{cc}
0 \pm 1 \\
\pm 1 0
\end{array} \right),$$
позволяющие свести задачу к случаю отрезка, лежащего в первом октанте (пример см. на рис. 3.2, этап
2, в нем матрица имеет вид$$\left( \begin{array}{cc}
0 1 \\
1 0
\end{array} \right).$$
Назовем такой случай каноническим, в дальнейшем будут рассмотрены алгоритмы для этого случая. В каноническом случае процесс рисования 8 -связной линии можно закодировать последовательностью вида: sdssd... (см. рис. 3.3), где
s - горизонтальное смещение;d - диагональное смещение.
(рис 3.2) Переход к каноническому случаю в два этапа.Эквивалентно этой последовательности можно сопоставить бинарный код, где 0 соответствует s, а 1 соответствует d. Такой код для рисования отрезка $$(0, 0) \to (p, q), p > q \in \mathbb{N}$$ называется кодом Ротштейна [46] для $$\frac{p}{q}$$.
Пусть - функция, закрашивающая точку растра с координатами (x,y).
(рис 3.3) Кодирование закрашивания отрезка (или код Ротштейна).Алгоритм Цифровой дифференциальный анализатор (англ. DDA - Digital
Для начала, пусть P1 = (1, 0) ; P2 = (1, 1). Для определения того, какой из пикселей, - P1 или P2, - следует закрасить, сравним расстояния до них. В силу подобия треугольников, образованных пересечением рисуемого отрезка, прямой x = 1 и перпендикулярами из P1 и P2 на отрезок (см. рис. 3.4), достаточно сравнить e (ординату пересечения отрезка c прямой x = 1 ) с $$\frac{1}{2}$$. Далее, для следующего шага алгоритм работает аналогично с учетом изменения e - ординаты пересечения отрезка со следующей вертикальной прямой $$x = k, k \in \mathbb{N}$$.

(рис 3.1) Цифровой дифференциальный анализатор.(рис 3.4) Цифровой дифференциальный анализатор// Координаты концов отрезка - (0,0) и (a,b) e = b/a; // Текущая ордината delta_e = b/a; // Приращение ординаты // (x,y) - Координаты текущей точки x = 0; y = 0; while( x < a ) { plot(x, y); if( e > 1/2 ) { // d : диагональное смещение x++; y++; // т.к. произошло смещение по y на 1 вверх e += delta_e - 1; } else { // s : горизонтальное смещение x++; e += delta_e; } }
Недостатком данного алгоритма является то, что он работает с числами с плавающей точкой.
Брезенхем [16] модифицировал алгоритм DDA, чтобы он работал в целых числах. Модифицируем алгоритм следующим образом:
e на $$\frac{1}{2}$$, чтобы сравнивать с 0 ;e и $$\Delta e$$ на 2a: e0 = 2b - a, $$\Delta e = 2b$$Приходим к следующему алгоритму:
// Координаты концов отрезка - (0,0) и (a,b)
e = 2b - a;
delta_eS = 2b;
delta_eD = 2b - 2a;
x = 0; y = 0; // (x,y) - Координаты текущей точки
while(x < a)
{
plot(x, y);
if(e > 0)
{ // d : диагональное смещение
x++; y++;
e += delta_eD;
}
else
{ // s : горизонтальное смещение
x++;
e += delta_eS;
}
}
Алгоритм Брезенхема был создан им для вывода отрезков на цифровых инкрементальных
Этот алгоритм гораздо менее эффективен с вычислительной точки зрения, чем алгоритм Брезенхема, однако обладает красивой
Будем работать со строками, кодирующими последовательность закраски (т.е. состоящими из символов s и d, определенных выше).
Определим две операции над такими строками:
$$"ssds" \oplus "sddd " = "ssdssddd "$$
$$\sim ("ssdds") = "sddss"$$
// Координаты концов отрезка - (0,0) и (a,b)
y = b;
x = a - b;
m1 = "s";
m2 = "d";
while( x \ne y )
{
if( x > y )
{
x = x - y;
m2 = m1 (+) ~ m2;
}
else
{
y = y - x;
m1 = m2 (+) ~ m1;
}
}
После завершения работы алгоритма $$m = m_2\oplus \sim m_1$$ задает нужную последовательность сдвигов.
Для отрезка с нецелочисленными координатами концов будем строить соответствующую 4-связную линию на растре.
(рис 3.5) Рисование отрезка с нецелочисленными координатами концов.Существует два подхода.
где A и B - концевые точки, c > 0 - некий масштабный коэффициент. Сделаем c достаточно большим целым числом, чтобы уменьшить ошибки округления. Тогда рассмотрим
$$\Delta h = \frac{c}{x_B-x_A}$$
- приращение t, при сдвиге на 1 пиксель по x ;
$$\Delta v = \frac{c}{y_B-y_A}$$
- приращение t, при сдвиге на 1 пиксель по y.
Будем сравнивать текущие значения h и v, а затем, в зависимости от этого, делать шаг по x или y и придавать соответствующие приращения h и v. Алгоритм закончится, когда h или v превысит c.

(рис 3.4) Изменение параметров h и v.(рис 3.6) Алгоритм отображения отрезка с нецелочисленными координатами концовx = 0; y = 0; // Канонический случай: начальная точка // лежит в [0, 1) (+) [0, 1) /* Приращения t, соответствующие смещениям от начальной точки до границ первого пикселя. */ h = delta_h * (1 - xA); // delta_h0 v = delta_v * (1 - yA); // delta_v0 while( (h < c) AND (v < c) ) { plot(x, y); if( h < v ) { // Сдвиг по горизонтали x++; h += delta_h; } else if( h > v ) { // Сдвиг по вертикали y++; v += delta_v; } else { // h = v : Вырожденный случай (см. рис. 3.5) // рисуем произвольный из двух возможных пикселей, // например, верхний: plot(x,y+1); x++; y++; h += delta_h; v += delta_v; } }
Замечание. Приведенный выше алгоритм легко обобщается на n -мерный случай.
Для начала перейдем к канонической системе координат, в которой центр окружности совпадает с началом координат. Тогда можно заметить, что в силу симметрии окружности относительно прямых, разделяющих октанты, достаточно построить растровое представление в одном октанте, а затем с помощью симметрий получить изображения в других октантах (см. рис. 3.7). Будем пользоваться заданием окружности в виде неявной функции: x2 + y2 - R2 = 0.
(рис 3.7) Симметрии при изображении окружности.Пусть f(x, y) = x2 + y2 - R2. Будем рисовать часть окружности в 4 -м октанте, начиная с точки (-R, 0) (см. рис. 3.7, показано стрелкой).
Пусть $$R \in \mathbb{N}$$, тогда $$f(x, y) \in \mathbb{Z} \text{ для } x \in \mathbb{Z}, y \in \mathbb{Z}$$. Пусть функция plot8(x, y) отображает на растре все 8 точек, полученных из (x, y) с помощью симметрий.
Будем рассуждать подобно алгоритму Брезенхема для отрезков (с соответствующими поправками на 4 -й октант) [17]. Из двух возможных пикселов в 4 -м октанте (соответствующих вертикальному и диагональному смещениям, которые обозначаются аналогично прежним s и d, см. рис. 3.10) будем выбирать тот, расстояние от окружности до которого меньше.
(рис 3.8) Расстояния до окружности.Для того чтобы выбрать один из двух возможных пикселей, будем сравнивать расстояния от них до окружности: где расстояние меньше - тот пиксел и будет искомым. В примере на рис. 3.8 сравниваются расстояния от точек S(xs, ys) и D(xd, yd) до окружности с радиусом R. Из евклидовой метрики получаем:
Но вычисление квадратного корня - вычислительно трудоемкая операция, поэтому при достаточно больших R мы будем заменять сравнение расстояний сравнением приближенных значений их квадратов (см. рис. 3.9):
(рис 3.9) Приближенное сравнение расстояний.Уменьшим два слагаемых на приблизительно одинаковые величины:
$$- 2R\sqrt{x_s^2 + y_s^2}$$ заменим на $$-2R \cdot R$$,
$$+ 2R\sqrt{x_d^2 + y_d^2}$$ заменим на $$+2\sqrt{x_d^2 + y_d^2} \cdot \sqrt{x_d^2 + y_d^2}$$
получим
$$(\Delta R_s)^2-(\Delta R_d)^2 \approx x_s^2 + y_s^2 - 2R \cdot R + R^2 - \\ - x_d^2 - y_d^2 + 2\sqrt{x_d^2 + y_d^2} \cdot \sqrt{x_d^2 + y_d^2} - R^2 = \\ = x_s^2 + y_s^2 + x_d^2 + y_d^2 - 2R^2.$$Таким образом, приближенно
D ближе к окружности, чем S $$\Leftrightarrow$$$$x_s^2 + y_s^2 + x_d^2 + y_d^2 - 2R^2 > 0;$$
S ближе к окружности, чем D $$\Leftrightarrow$$$$x_s^2 + y_s^2 + x_d^2 + y_d^2 - 2R^2 < 0.$$
(рис 3.10) Алгоритм Брезенхема для окружности.Пусть (x, y) - текущий пиксель. Обозначим
$$\Delta F(s) = ( \Delta F \text{ при переходе }s\colon (x, y) \to (x, y + 1) ) = \\ = f(x, y + 2) + f(x + 1, y + 2) - f(x, y + 1)- \\ - f(x + 1, y + 1)\\ = 4y + 6,$$
$$\Delta F(d) = ( \Delta F \text{ при переходе } d\colon (x, y) \to (x + 1, y + 1) ) = \\ = f(x + 1, y + 2) + f(x + 2, y + 2) - f(x, y + 1)- \\ - f(x + 1, y + 1) \\ = 4x + 4y + 10.$$
Тогда из двух возможных смещений d и s выберем.
(x + 1, y + 1) ближе к
окружности, чем (x, y + 1):d: Переходим в (x + 1, y + 1) и придаем соответствующие
приращения F, $$\Delta F(s)$$, $$\Delta F(d)$$:
(x, y+1) ближе к окружности,
чем (x + 1, y + 1):s: Переходим в (x, y + 1) и придаем соответствующие
приращения F, $$\Delta F(s)$$, $$\Delta F(d)$$:
Если мы начинаем из (-R, 0), то начальные значения будут следующими:
Легко видеть, что в алгоритме все величины, связанные с F, кроме F начального, будут кратны 2. Но, если мы поделим все эти величины на 2 (в дальнейшем значения всех величин уже понимаются в этом смысле), то $$F_{нач} = \frac{1}{2}+1-R$$. Так как приращения F могут быть только целочисленными, то $$F = \frac{1}{2} +T$$, где $$T \in \mathbb{Z}$$ ; т.е. если отнять $$\frac{1}{2}$$ от всех значений, то знак F не изменится для всех T, кроме T = 0. Для того чтобы результат сравнения остался прежним, будем считать, что F = 0 теперь соответствует смещению s.
x = -r; y = 0;
F = 1-r;
delta_Fs = 3;
delta_Fd = 5-2*r;
while( x + y < 0 )
{
plot8( x, y );
if( F > 0 )
{
// d: Диагональное смещение
F += delta_Fd;
x++; y++;
delta_Fs += 2;
delta_Fd += 4;
}
else
{
// s: Вертикальное смещение
F += delta_Fs;
y++;
delta_Fs += 2;
delta_Fd += 2;
}
}
Размерность вычислений этого алгоритма (т.е. отношение максимальных модулей значений величин, с которыми он оперирует к модулям исходных данных (в данном случае R )) равна 2.
Прежде всего отметим, что у эллипса, в отличие от окружности, всего 2 оси симметрии, поэтому по точкам придется строить уже 2 октанта (см. рис. 3.11).
(рис 3.11) Изображение эллипса.Будем рассуждать подобно алгоритму Брезенхема для окружностей.
Неявная функция, задающая эллипс, имеет вид
$${{\left( \frac{x}{a} \right)}^2 + {\left( \frac{y}{b} \right)}^2 -1 = 0, a > b}\\ {b^{2x2} + a^{2y2} - a^{2b2} =0}$$Введем f(x, y) = b2x2 + a2y2 - a2b2.
Аналогично алгоритму для окружности можно сравнивать f для двух возможных вариантов. Подробный вывод оставляем читателю в качестве упражнения.
Воспользуемся тем, что эллипс с параметрами a, b (пусть a > b ) получается из окружности радиуса a сжатием по оси y в a/b раз. Построим алгоритм, который является некой комбинацией алгоритмов Брезенхема для окружности и для отрезка (см. рис. 3.12).

(рис 3.13) Построение эллипса путем сжатия окружности.(рис 3.12) Смешанная связность.Начнем из точки (a, 0) на окружности и из точки (0, 0) на отрезке. Будем строить эллипс точно так же, как окружность, но смещать текущую точку по y только в том случае, когда такое смещение происходит в текущем шаге уже для отрезка, т.е. построение отрезка как раз и является реализацией сжатия в a/b раз (точнее, его дискретной аппроксимацией). Этот алгоритм тоже имеет недостаток: возможная смешанная связность полученной линии (см. рис. 3.13).
Этот раздел посвящен
Пусть у нас есть некоторая кривая, и мы хотим построить ее изображение на растровой решетке. Возникает вопрос: какие из ближайших пикселей следует закрашивать? В данной и следующей лекциях мы рассмотрим случай построения на монохромном растре, когда возможны только два уровня интенсивности закраски пикселя - "полностью закрашен" или "полностью не закрашен". Если же допустимы несколько уровней интенсивности, то можно растеризовывать более аккуратно, уменьшая эффекты алиасинга (т.е. ступенчатости), см. раздел 7.2.
(рис 3.1) Изображение кривых на растре.Пусть (x0, y0) - фиксированный пиксель, а (x, y) - некоторый другой пиксель на плоскости. Тогда для определения их близости вводятся следующие понятия:
1. 4-связность|x-x0|+|y-y0|=1 |
![]() |
2. 8-связностьmax{|x-x0|, |y-y0|}=1
|
![]() |
В дальнейших рассуждениях расстояние будем считать заданным стандартной евклидовой dist(P1,P2) = ((x1 - x2)2 + (y1 - y2)2)1/2
Пусть наш отрезок - это AB. Перейдем от системы координат Oxy к Ax'y' (см. рис. 3.2, этап 1). Отрезок может лежать в любом из 8 октантов, но всегда существуют симметрии относительно осей,
разделяющих эти октанты, симметрии определяются матрицами$$\left( \begin{array}{cc}
\pm 1 0 \\
0 \pm 1
\end{array} \right)$$
и$$\left( \begin{array}{cc}
0 \pm 1 \\
\pm 1 0
\end{array} \right),$$
позволяющие свести задачу к случаю отрезка, лежащего в первом октанте (пример см. на рис. 3.2, этап
2, в нем матрица имеет вид$$\left( \begin{array}{cc}
0 1 \\
1 0
\end{array} \right).$$
Назовем такой случай каноническим, в дальнейшем будут рассмотрены алгоритмы для этого случая. В каноническом случае процесс рисования 8 -связной линии можно закодировать последовательностью вида: sdssd... (см. рис. 3.3), где
s - горизонтальное смещение;d - диагональное смещение.
(рис 3.2) Переход к каноническому случаю в два этапа.Эквивалентно этой последовательности можно сопоставить бинарный код, где 0 соответствует s, а 1 соответствует d. Такой код для рисования отрезка $$(0, 0) \to (p, q), p > q \in \mathbb{N}$$ называется кодом Ротштейна [46] для $$\frac{p}{q}$$.
Пусть - функция, закрашивающая точку растра с координатами (x,y).
(рис 3.3) Кодирование закрашивания отрезка (или код Ротштейна).Алгоритм Цифровой дифференциальный анализатор (англ. DDA - Digital
Для начала, пусть P1 = (1, 0) ; P2 = (1, 1). Для определения того, какой из пикселей, - P1 или P2, - следует закрасить, сравним расстояния до них. В силу подобия треугольников, образованных пересечением рисуемого отрезка, прямой x = 1 и перпендикулярами из P1 и P2 на отрезок (см. рис. 3.4), достаточно сравнить e (ординату пересечения отрезка c прямой x = 1 ) с $$\frac{1}{2}$$. Далее, для следующего шага алгоритм работает аналогично с учетом изменения e - ординаты пересечения отрезка со следующей вертикальной прямой $$x = k, k \in \mathbb{N}$$.

(рис 3.1) Цифровой дифференциальный анализатор.(рис 3.4) Цифровой дифференциальный анализатор// Координаты концов отрезка - (0,0) и (a,b) e = b/a; // Текущая ордината delta_e = b/a; // Приращение ординаты // (x,y) - Координаты текущей точки x = 0; y = 0; while( x < a ) { plot(x, y); if( e > 1/2 ) { // d : диагональное смещение x++; y++; // т.к. произошло смещение по y на 1 вверх e += delta_e - 1; } else { // s : горизонтальное смещение x++; e += delta_e; } }
Недостатком данного алгоритма является то, что он работает с числами с плавающей точкой.
Брезенхем [16] модифицировал алгоритм DDA, чтобы он работал в целых числах. Модифицируем алгоритм следующим образом:
e на $$\frac{1}{2}$$, чтобы сравнивать с 0 ;e и $$\Delta e$$ на 2a: e0 = 2b - a, $$\Delta e = 2b$$Приходим к следующему алгоритму:
// Координаты концов отрезка - (0,0) и (a,b)
e = 2b - a;
delta_eS = 2b;
delta_eD = 2b - 2a;
x = 0; y = 0; // (x,y) - Координаты текущей точки
while(x < a)
{
plot(x, y);
if(e > 0)
{ // d : диагональное смещение
x++; y++;
e += delta_eD;
}
else
{ // s : горизонтальное смещение
x++;
e += delta_eS;
}
}
Алгоритм Брезенхема был создан им для вывода отрезков на цифровых инкрементальных
Этот алгоритм гораздо менее эффективен с вычислительной точки зрения, чем алгоритм Брезенхема, однако обладает красивой
Будем работать со строками, кодирующими последовательность закраски (т.е. состоящими из символов s и d, определенных выше).
Определим две операции над такими строками:
$$"ssds" \oplus "sddd " = "ssdssddd "$$
$$\sim ("ssdds") = "sddss"$$
// Координаты концов отрезка - (0,0) и (a,b)
y = b;
x = a - b;
m1 = "s";
m2 = "d";
while( x \ne y )
{
if( x > y )
{
x = x - y;
m2 = m1 (+) ~ m2;
}
else
{
y = y - x;
m1 = m2 (+) ~ m1;
}
}
После завершения работы алгоритма $$m = m_2\oplus \sim m_1$$ задает нужную последовательность сдвигов.
Для отрезка с нецелочисленными координатами концов будем строить соответствующую 4-связную линию на растре.
(рис 3.5) Рисование отрезка с нецелочисленными координатами концов.Существует два подхода.
где A и B - концевые точки, c > 0 - некий масштабный коэффициент. Сделаем c достаточно большим целым числом, чтобы уменьшить ошибки округления. Тогда рассмотрим
$$\Delta h = \frac{c}{x_B-x_A}$$
- приращение t, при сдвиге на 1 пиксель по x ;
$$\Delta v = \frac{c}{y_B-y_A}$$
- приращение t, при сдвиге на 1 пиксель по y.
Будем сравнивать текущие значения h и v, а затем, в зависимости от этого, делать шаг по x или y и придавать соответствующие приращения h и v. Алгоритм закончится, когда h или v превысит c.

(рис 3.4) Изменение параметров h и v.(рис 3.6) Алгоритм отображения отрезка с нецелочисленными координатами концовx = 0; y = 0; // Канонический случай: начальная точка // лежит в [0, 1) (+) [0, 1) /* Приращения t, соответствующие смещениям от начальной точки до границ первого пикселя. */ h = delta_h * (1 - xA); // delta_h0 v = delta_v * (1 - yA); // delta_v0 while( (h < c) AND (v < c) ) { plot(x, y); if( h < v ) { // Сдвиг по горизонтали x++; h += delta_h; } else if( h > v ) { // Сдвиг по вертикали y++; v += delta_v; } else { // h = v : Вырожденный случай (см. рис. 3.5) // рисуем произвольный из двух возможных пикселей, // например, верхний: plot(x,y+1); x++; y++; h += delta_h; v += delta_v; } }
Замечание. Приведенный выше алгоритм легко обобщается на n -мерный случай.
Для начала перейдем к канонической системе координат, в которой центр окружности совпадает с началом координат. Тогда можно заметить, что в силу симметрии окружности относительно прямых, разделяющих октанты, достаточно построить растровое представление в одном октанте, а затем с помощью симметрий получить изображения в других октантах (см. рис. 3.7). Будем пользоваться заданием окружности в виде неявной функции: x2 + y2 - R2 = 0.
(рис 3.7) Симметрии при изображении окружности.Пусть f(x, y) = x2 + y2 - R2. Будем рисовать часть окружности в 4 -м октанте, начиная с точки (-R, 0) (см. рис. 3.7, показано стрелкой).
Пусть $$R \in \mathbb{N}$$, тогда $$f(x, y) \in \mathbb{Z} \text{ для } x \in \mathbb{Z}, y \in \mathbb{Z}$$. Пусть функция plot8(x, y) отображает на растре все 8 точек, полученных из (x, y) с помощью симметрий.
Будем рассуждать подобно алгоритму Брезенхема для отрезков (с соответствующими поправками на 4 -й октант) [17]. Из двух возможных пикселов в 4 -м октанте (соответствующих вертикальному и диагональному смещениям, которые обозначаются аналогично прежним s и d, см. рис. 3.10) будем выбирать тот, расстояние от окружности до которого меньше.
(рис 3.8) Расстояния до окружности.Для того чтобы выбрать один из двух возможных пикселей, будем сравнивать расстояния от них до окружности: где расстояние меньше - тот пиксел и будет искомым. В примере на рис. 3.8 сравниваются расстояния от точек S(xs, ys) и D(xd, yd) до окружности с радиусом R. Из евклидовой метрики получаем:
Но вычисление квадратного корня - вычислительно трудоемкая операция, поэтому при достаточно больших R мы будем заменять сравнение расстояний сравнением приближенных значений их квадратов (см. рис. 3.9):
(рис 3.9) Приближенное сравнение расстояний.Уменьшим два слагаемых на приблизительно одинаковые величины:
$$- 2R\sqrt{x_s^2 + y_s^2}$$ заменим на $$-2R \cdot R$$,
$$+ 2R\sqrt{x_d^2 + y_d^2}$$ заменим на $$+2\sqrt{x_d^2 + y_d^2} \cdot \sqrt{x_d^2 + y_d^2}$$
получим
$$(\Delta R_s)^2-(\Delta R_d)^2 \approx x_s^2 + y_s^2 - 2R \cdot R + R^2 - \\ - x_d^2 - y_d^2 + 2\sqrt{x_d^2 + y_d^2} \cdot \sqrt{x_d^2 + y_d^2} - R^2 = \\ = x_s^2 + y_s^2 + x_d^2 + y_d^2 - 2R^2.$$Таким образом, приближенно
D ближе к окружности, чем S $$\Leftrightarrow$$$$x_s^2 + y_s^2 + x_d^2 + y_d^2 - 2R^2 > 0;$$
S ближе к окружности, чем D $$\Leftrightarrow$$$$x_s^2 + y_s^2 + x_d^2 + y_d^2 - 2R^2 < 0.$$
(рис 3.10) Алгоритм Брезенхема для окружности.Пусть (x, y) - текущий пиксель. Обозначим
$$\Delta F(s) = ( \Delta F \text{ при переходе }s\colon (x, y) \to (x, y + 1) ) = \\ = f(x, y + 2) + f(x + 1, y + 2) - f(x, y + 1)- \\ - f(x + 1, y + 1)\\ = 4y + 6,$$
$$\Delta F(d) = ( \Delta F \text{ при переходе } d\colon (x, y) \to (x + 1, y + 1) ) = \\ = f(x + 1, y + 2) + f(x + 2, y + 2) - f(x, y + 1)- \\ - f(x + 1, y + 1) \\ = 4x + 4y + 10.$$
Тогда из двух возможных смещений d и s выберем.
(x + 1, y + 1) ближе к
окружности, чем (x, y + 1):d: Переходим в (x + 1, y + 1) и придаем соответствующие
приращения F, $$\Delta F(s)$$, $$\Delta F(d)$$:
(x, y+1) ближе к окружности,
чем (x + 1, y + 1):s: Переходим в (x, y + 1) и придаем соответствующие
приращения F, $$\Delta F(s)$$, $$\Delta F(d)$$:
Если мы начинаем из (-R, 0), то начальные значения будут следующими:
Легко видеть, что в алгоритме все величины, связанные с F, кроме F начального, будут кратны 2. Но, если мы поделим все эти величины на 2 (в дальнейшем значения всех величин уже понимаются в этом смысле), то $$F_{нач} = \frac{1}{2}+1-R$$. Так как приращения F могут быть только целочисленными, то $$F = \frac{1}{2} +T$$, где $$T \in \mathbb{Z}$$ ; т.е. если отнять $$\frac{1}{2}$$ от всех значений, то знак F не изменится для всех T, кроме T = 0. Для того чтобы результат сравнения остался прежним, будем считать, что F = 0 теперь соответствует смещению s.
x = -r; y = 0;
F = 1-r;
delta_Fs = 3;
delta_Fd = 5-2*r;
while( x + y < 0 )
{
plot8( x, y );
if( F > 0 )
{
// d: Диагональное смещение
F += delta_Fd;
x++; y++;
delta_Fs += 2;
delta_Fd += 4;
}
else
{
// s: Вертикальное смещение
F += delta_Fs;
y++;
delta_Fs += 2;
delta_Fd += 2;
}
}
Размерность вычислений этого алгоритма (т.е. отношение максимальных модулей значений величин, с которыми он оперирует к модулям исходных данных (в данном случае R )) равна 2.
Прежде всего отметим, что у эллипса, в отличие от окружности, всего 2 оси симметрии, поэтому по точкам придется строить уже 2 октанта (см. рис. 3.11).
(рис 3.11) Изображение эллипса.Будем рассуждать подобно алгоритму Брезенхема для окружностей.
Неявная функция, задающая эллипс, имеет вид
$${{\left( \frac{x}{a} \right)}^2 + {\left( \frac{y}{b} \right)}^2 -1 = 0, a > b}\\ {b^{2x2} + a^{2y2} - a^{2b2} =0}$$Введем f(x, y) = b2x2 + a2y2 - a2b2.
Аналогично алгоритму для окружности можно сравнивать f для двух возможных вариантов. Подробный вывод оставляем читателю в качестве упражнения.
Воспользуемся тем, что эллипс с параметрами a, b (пусть a > b ) получается из окружности радиуса a сжатием по оси y в a/b раз. Построим алгоритм, который является некой комбинацией алгоритмов Брезенхема для окружности и для отрезка (см. рис. 3.12).

(рис 3.13) Построение эллипса путем сжатия окружности.(рис 3.12) Смешанная связность.Начнем из точки (a, 0) на окружности и из точки (0, 0) на отрезке. Будем строить эллипс точно так же, как окружность, но смещать текущую точку по y только в том случае, когда такое смещение происходит в текущем шаге уже для отрезка, т.е. построение отрезка как раз и является реализацией сжатия в a/b раз (точнее, его дискретной аппроксимацией). Этот алгоритм тоже имеет недостаток: возможная смешанная связность полученной линии (см. рис. 3.13).
Для получения официальных документов о завершении программы дополнительного профессионального образования (удостоверения о повышении квалификации, дипломов о профессиональной переподготовке и MBA) необходимо предоставить:
Внимание! Вы можете не заказывать доставку бумажной версии официального документы, а скачать его в электронном виде и распечатать самостоятельно. Информация о выданном документе в течение 1 месяца загружается в Федеральную информационную систему «Федеральный реестр сведений о документах об образовании и (или) о квалификации, документах об обучении» - ФИС ФРДО.
Доступ на новый сайт осуществляется с использованием адреса электронной почты, который был указан вами при регистрации на "старом". Мы постарались перенести все ваши данные с прежнего ресурса, однако не исключена вероятность потери части информации.
При возникновении проблемы со входом, воспользуйтесь функцией сброса пароля
Если вы обнаружите несоответствия, пожалуйста, сообщите нам.