Geometría bidimensional

Vamos a a ver una serie de técnicas matemáticas que nos van a permitir dibujar rectas, curvas, puntos, en el plano. Además, trabajaremos con figuras, y buscaremos procedimientos que nos permitan saber si un punto del plano es interior o exterior a una figura convexa.

Nos vamos a apoyar en la geometría vectorial afin y euclídea, de las que iré explicando los elementos que vamos a necesitar para poder diseñar los diferentes programas.

Rectas y puntos

La ecuación de una recta en el plano tiene la expresión ax + by + c = 0, en donde a, b, c son números reales fijos y conocidos. .Los puntos del plano (x, y) que no cumplen la ecuación no están en la recta.

Otra forma de dar la ecuación de una recta, es mediante su forma vectorial, que nos va a ser más útil desde el punto de vista de los gráficos por ordenador. Una recta en forma vectorial tiene la forma (x, y) = (m, n) + t(vx, vy) en donde (m, n) es un punto de la recta, y (vx, vy) es un vector direccional de la recta. El vector direccional de la recta ax + by + c = 0 es (vx, vy) = (-b, a).

La pendiente de la recta es p = -b/a. La pendiente nos da información sobre la recta

Para representar un recta en el plano en forma vectorial, necesitamos un punto y un vector direccional. Al darle valores a t, en la expresión (x, y) = (m, n) + t(vx, vy) vamos obteniendo puntos de la recta ¿Cómo podemos usar la ecuación de la recta en forma vectorial, para representar una recta? Metiendo en un bucle de variable t, la expresión (m+t*vx, n+t*vy), y dándole a t valores muy cercanos. Pero hay un problema: si el vector tiene un módulo muy grande nos podemos salir de la pantalla, en pocas iteraciones, con lo que no veremos la recta (y además es muy posible que obtengamos un mensaje de error). La solución está, en conseguir que el vector direccional siempre tenga módulo 1, y para ello, basta hacerlo unitario.

Si tenemos un vector, (vx, vy), el vector de igual dirección y sentido de módulo 1 es (vx/modu, vy/modu), siendo modu = raiz ((vx)^2+(vy^2)). Recordemos que nuestra pantalla gráfica tiene esta forma:

A partir de ahora vamos a suponer que es cuadrada, y que por tanto ancho = alto = lado. Además supondremos que las unidades de la pantalla están en pixeles, y en nuestro caso lado = ancho =alto = 400 pixeles.

El siguiente programa dibuja una recta que pasa por el punto (m, n) , de vector direccional (vx, vy). Los ejes coordenados van a tener un rango entre -10 y 10 unidades, tanto en vertical como en horizontal.

En todos estos programas tienes que tener cuidado para que no se produzca error por desbordamiento, es decir, que alguna variable tome un valor que dé coordenadas de puntos que salgan fuera del área gráfica. Por eso aparece la linea que evita esa posibilidad

Programa recta(m,n,vx,vy)

Obtener el centro de la pantalla (cx, cy)

modu = Sqr(vx ^ 2 + vy ^ 2)
px = m * 20: py = n * 20

para t entre -lado/2 y lado/2, con incremento 0.01
{
Si el punto está fuera de la zona gráfica continua con el siguiente t
PSet (cx + px + t * vx / modu, cy - py - t * vy / modu)
}

Este podría ser el resultado de nuestro programa para una recta que pasa por (2,3) de vector direccional (2, -1). Observa que los valores de t, para este caso no consiguen que a recta sea "completa", es decir que sea loa mayor posible dentro del cuadrado de dibujo.¿Cómo se podría conseguir que lo fuera?

Como ves, el programa dibuja también la unidades en los ejes, y el punto inicial (2, 3)

Dibujando funciones

Esta misma idea nos va a permitir dibujar una función. Por ejemplo la función y = sen x / x. Se trata de dibujar sobre los ejes los pares de puntos (t, sen(t)/t). Ahora bien, como esta función tiene un recorrido muy pequeño (siempre se mantiene entre 1 y -1), para conseguir un dibujo más "visible", hemos de agrandarla verticalmente. Además podemos hacer que el período de la función seno sea pequeño, para conseguir que corte al eje X más veces. El siguiente programa consigue lo que se ha propuesto.

Programa funcion(factor,periodo)

obtener el centro de la pantalla (cx, cy)

para t entre -lado/2 y lado/2, con incremento 0.01
{
Si t =0 , continua con el siguiente t 'ya que la función no está definida en 0
Si el punto está fuera de la zona gráfica continua con el siguiente t
PSet (cx + t, cy - factor * Sin(periodo * t) / t)
}

Y da lugar al siguiente resultado, para factor = 1000, 5000, 10000, periodo = 100, sin borrar en cada ejecución, la imagen. A la derecha tienes la gráfica de la función obtenida con DERIVE, en la que se observa que el recorrido, es efectivamente muy pequeño.

La recta divide al plano en tres regiones

La distancia desde un punto P(xo,yo), a la recta r: ax + by + c = 0, viene dada por la relación

d(P, r) = (a · xo + b · yo + c) /raiz(a2+b2)

Este valor, por definición distancia, se toma en valor absoluto, pero d(P, r), puede ser positivo, negativo, o nulo. Entonces

El siguiente ejemplo explica las ideas anteriores

observa que para el ejemplo de la izquierda el origen (0, 0), está en la zona negativa, y para el ejemplo de la derecha está en la zona positiva. En ambos casos el origen está en la zona que marca el vector (a, b), que en el primer caso es (-2, 3) y en segundo es (2, -3).

Si llamamos f(x, y) = ax + by + c, entonces tenemos un procedimiento para saber si dos puntos están o no al mismo lado de la recta. Para P(x1, y1), Q(x2, y2), se tendrá:

Puntos interiores y exteriores a un polígono convexo

Supongamos una figura delimitada por segmentos, que a su vez están delimitados por vértices. Buscamos una forma de saber si un punto cualquiera está o no dentro de la figura. La forma de resolver el problema depende de si la figura es cóncava o convexa. Sobre estas ideas tienes un buen resumen en el punto 14 de sección "para contar" en esta misma página web (aquí). Supondremos que la figura es convexa.

Un polígono está delimitado por puntos Pi(xi, yi), de manera que cada Pi, está unido a Pi+1. Si el polígono tiene n puntos, entonces Pn, está unido a P1

Sea fi(x, y) la recta que une el punto Pi con el punto Pi+1, siendo fn(x, y) la recta que une Pn con Po. Supongamos que conocemos un punto (m, n) interior al polígono. ¿Cómo podemos saber si (m1, n1), es también interior?

En nuestro caso vamos a considerar el punto (0, 0) como punto de referencia: en este punto las fi(0, 0), toman todas valor negativo. Por tanto, un punto cualquiera (m, n) será interior al polígono si las fi(m, n) son todas negativas.

Si alguno de los valores es positivo el punto será exterior, y si es cero, estará en la frontera. Concretando:

  • f1(1, 1) = -3 + 4 - 5 < 0
  • f2(1, 1) = - 3 - 4 - 13 < 0
  • f3(1, 1) =  4 - 1 - 8 < 0
  • f4(1, 1) = 1 + 1 - 4 < 0
El punto (1, 1) es interior al polígono convexo
  • f1(-3, 3) = 9 + 12 - 5 > 0
  • f2(-3, 3) = 9 - 12 - 13 < 0
  • f3(-3, 3) =  -12  - 3 - 8 < 0
  • f4(-3, 3) = -6 + 3 - 4 < 0
El punto (-3, 3) es exterior al polígono convexo

como en casos anteriores, todas estas ideas se deben convertir en un programa de ordenador. Piensa tú en cómo debería ser el código para resolver estos problemas. Algunas de estas ideas las vamos a necesitar en posteriores desarrollos.

Si recordamos el procedimiento estocástico para obtener el área (véase el punto 14, en la sección "para contar ...") de un polígono, podemos conseguir que el programa calcule aproximadamente el área del polígono. Aquí tienes un programa, que realiza los objetivos planteados a lo largo de este apartado (para instalarlo, descomprime a una carpeta y ejecuta el setup).

Está diseñado para que si el punto cae en la frontera, se pinte de amarillo, pero esto es prácticamente imposible ¿Por qué?

Cada vez que aprietes el botón Bombardeo, se generan una serie de puntos que se lanzan sobre un cuadrilátero, dibujado dentro de un cuadrado centrado en (0, 0) y de lado 20 unidades. Al lanzar muchos puntos sobre el cuadrado irás mejorando la aproximación a la superficie de polígono.

Por supuesto, lo importante es que lo hagas tú. Pero aquí tienes el resultado de un "bombardeo" sobre el cuadrilátero de la figura. Compara el valor aproximado con la verdadera superficie.