Перейти до основного вмісту

Обчислення площі простого многокутника за O(N)O(N)

Нехай задано простий многокутник (тобто без самоперетинів, не обов'язково опуклий). Потрібно обчислити його площу за заданими вершинами.

Коли підходить цей алгоритм?
  • Многокутник заданий упорядкованим списком вершин (за або проти годинникової стрілки)?
  • Многокутник простий, тобто його сторони не самоперетинаються?
  • Потрібна саме площа за вершинами, а не кількість цілочислових точок усередині? (якщо ні → Теорема Піка)

Метод 1

Це легко зробити, якщо пройтися по всіх ребрах і додати площі трапецій, обмежених кожним ребром та віссю xx. Площу слід брати зі знаком, щоб зайва площа скорочувалася. Отже, формула така:

A=(p,q)edges(pxqx)(py+qy)2A = \sum_{(p,q)\in \text{edges}} \frac{(p_x - q_x) \cdot (p_y + q_y)}{2}

Код:

double area(const vector<point>& fig) {
double res = 0;
for (unsigned i = 0; i < fig.size(); i++) {
point p = i ? fig[i - 1] : fig.back();
point q = fig[i];
res += (p.x - q.x) * (p.y + q.y);
}
return fabs(res) / 2;
}

Метод 2

Ми можемо обрати довільну точку OO та пройтися по всіх ребрах, додаючи орієнтовану площу трикутника, утвореного ребром і точкою OO. Знову ж таки, завдяки знаку площі зайва площа скорочуватиметься.

Цей метод кращий, бо його можна узагальнити на складніші випадки (наприклад, коли деякі сторони є дугами, а не прямими лініями)

Відеоматеріали