Prefacio

Este libro constituye una obra en permanente actualización en las áreas de Procesamiento Digital de Imágenes (PDI) y Visión Computacional (VC), concebida como material didáctico interactivo para cursos de grado y posgrado en Computación, Ingeniería y áreas afines.

ImportanteDestacado

La obra se fundamenta en la metodología descrita en Zampirolli et al. (2025) — extensión de Zampirolli et al. (2024), trabajo premiado en la línea Recursos y Ambientes Educativos de la EduComp 2024. El contenido integra la biblioteca morph.py, desarrollada por el autor.

Este no es un libro estático. Su contenido evoluciona continuamente a medida que los ejemplos se mejoran, se incorporan nuevas secciones y los enfoques pedagógicos se refinan con base en la experiencia de uso y en la retroalimentación de estudiantes y docentes. De esta manera, la obra se trata como un proyecto en constante evolución, buscando acompañar tanto los avances tecnológicos como las mejores prácticas de enseñanza en PDI y VC.

Contexto de la primera edición

El contenido de esta edición fue elaborado entre mayo y agosto de 2026, durante la primera oferta de la asignatura de Procesamiento Digital de Imágenes basada en este material didáctico. La asignatura se impartió en dos grupos de grado —mayoritariamente compuestos por estudiantes de Ciencias de la Computación, en el período matutino— y en un grupo de posgrado en Ciencias de la Computación, todas en la UFABC. Esta primera edición representa el resultado de esa oferta inicial, consolidando el contenido desarrollado, probado y continuamente perfeccionado a lo largo del período lectivo.

La metodología de enseñanza adoptada siguió una secuencia estructurada en cada clase. Inicialmente, se proyectaba un video corto, con una duración media de 7 minutos, generado en Gemini Notebook, alternando entre la presentación de la parte conceptual del capítulo y la resolución de los Ejercicios de Programación (EP). En este segundo caso, casi todos los EP se resolvían durante la propia clase. A continuación, se presentaba un conjunto de aproximadamente 12 diapositivas, también generadas en Gemini Notebook, teniendo como fuentes el PDF completo del libro y el archivo morph.py. Estas diapositivas se producían a partir de un prompt específico para la generación del contenido teórico y práctico de cada capítulo.

Tras esta etapa inicial, quedaban aproximadamente 100 minutos de clase para la exploración de los dos cuadernos Colab del capítulo, uno teórico y otro práctico, con énfasis en los simuladores interactivos y en la ejecución de los bloques de código, permitiendo a los estudiantes modificar parámetros y observar sus efectos. En las clases realizadas en laboratorio, los estudiantes transferían las respuestas de los EP desarrolladas en Colab directamente a las actividades VPL de Moodle, en las cuales se sometían a la evaluación automática. Este proceso de publicación y utilización de los EP se presenta al final de este prefacio.

La evaluación continua incluyó simulacros quincenales, aplicados con SEB (Safe Exam Browser) en Moodle, que contenían EP similares a los de las listas de ejercicios. Cada simulacro otorgaba un bono del 5% sobre la nota final. Las dos pruebas de la asignatura también utilizaron SEB, pero estuvieron compuestas por preguntas parametrizadas generadas en MCTest, cuya descripción combina LaTeX y parámetros en el formato [[code:variable]], definidos en fragmentos de Python delimitados por [[def: ... ]] en la propia pregunta. Este proceso permitió generar 110 variaciones de examen, sorteadas individualmente entre los estudiantes.

El Apéndice A detalla la creación de estas preguntas en MCTest y su exportación a Moodle; el Apéndice B describe la configuración de las actividades VPL, incluido el proceso de publicación de los EP; el Apéndice C presenta la configuración de SEB para los simulacros y los exámenes; el Apéndice D describe la generación de los videos y diapositivas utilizados en las clases con Gemini Notebook; y el Apéndice E detalla el uso de Inteligencia Artificial (IA) en la generación de retroalimentación socrática para actividades formativas y evaluativas, complementando la corrección automática realizada por VPL.

Cómo se produce este libro

El contenido de este libro se desarrolla en Quarto y se almacena en la carpeta all del repositorio github.com/fzampirolli/pdi-vc. A partir de un único código fuente, el libro se genera automáticamente y se publica en diferentes formatos, presentados en Tabla 1.

Aunque la edición en PDF registra el estado de la obra al término de la primera oferta de la disciplina en 2026, el desarrollo del libro continúa de forma permanente. Con cada actualización del repositorio de GitHub, se generan automáticamente nuevas versiones de las páginas HTML, del PDF y de los notebooks, poniendo las mejoras inmediatamente a disposición de los lectores.

Tabla 1: Diferentes formatos de publicación generados automáticamente a partir del mismo código fuente.
Formato Descripción
HTML Versión para web, con simuladores interactivos y navegación entre capítulos: fzampirolli.github.io/pdi-vc/
PDF Versión adecuada para impresión o lectura offline: livro.pt.py.pdf
Notebooks (.ipynb) Compatibles con Jupyter y Google Colab, que permiten ejecutar, modificar y experimentar con los ejemplos de código y los Ejercicios de Programación (EPs). Un filtro personalizado mantiene las referencias cruzadas, la numeración de figuras y tablas, además de formatear automáticamente las citas según el estándar ABNT.

La obra se publica en diez combinaciones — cada ruta de código (Python y C++) en cinco idiomas (portugués, inglés, francés, español e italiano). Con la caché de traducción ya poblada, una regeneración completa (traducción, reejecución de los notebooks, renderizado de HTML y PDF y publicación) tarda unos 72 minutos, con un paralelismo real medio de ~5 procesos (pico de 8); la primera generación de un idioma nuevo, con la caché vacía, es mucho más lenta — unos 80 minutos por combinación, como se observó en las primeras generaciones de español e italiano. Tabla 2 resume cada combinación (ya con la caché poblada): número de páginas del PDF y tiempo de renderizado. Este tiempo total real es mucho menor que la suma de los tiempos de cada combinación por separado (más de 5 horas si se ejecutaran una por una): en una CPU con muchos núcleos, varias combinaciones se procesan al mismo tiempo, por lo que el tiempo total no es la simple suma de los tiempos individuales.

Tabla 2: Número de páginas del PDF y tiempo de renderizado por combinación (paralelismo real medio de ~5 procesos, pico de 8). La combinación base en Python/Portugués solo renderiza las salidas ya registradas en los notebooks-fuente; las demás reejecutan todo el código.
Combinación Ruta Idioma Páginas Tiempo de render.
py.pt Python Portugués (base) 654 ~7 min
py.en Python Inglés 644 ~31 min
py.fr Python Francés 666 ~31 min
py.es Python Español 666 ~31 min
py.it Python Italiano 658 ~31 min
cpp.pt C++ Portugués 434 ~26 min
cpp.en C++ Inglés 426 ~34 min
cpp.fr C++ Francés 434 ~38 min
cpp.es C++ Español 430 ~37 min
cpp.it C++ Italiano 428 ~35 min

Estado de validación. Solo la combinación py.pt (Python, portugués) es la fuente curada: es donde el autor escribe, revisa y valida todo el contenido. Las otras nueve combinaciones — las rutas en C++ y las traducciones al inglés, francés, español e italiano — se generan automáticamente, mediante traducción con un modelo de lenguaje y transpilación de código, y todavía requieren una revisión detallada. El punto más sensible es el texto incrustado en algunas figuras: donde aún no se ha producido la versión traducida, la imagen aparece con texto en portugués (cada figura traducida sigue el mismo sufijo de idioma que los demás archivos generados, por ejemplo imagen_en.png).

Las páginas HTML, el PDF y los notebooks disponibles en el proyecto reflejan siempre el estado más reciente del desarrollo. Cuando se publica una edición oficial, esta queda identificada mediante una etiqueta (tag) en el repositorio de GitHub, lo que permite reproducir exactamente el contenido correspondiente a esa edición. Así, el lector puede seguir tanto la evolución continua del proyecto como recuperar cualquier edición oficial publicada anteriormente.

git clone https://github.com/fzampirolli/pdi-vc.git
cd pdi-vc
git checkout <tag-de-la-version>

Cada capítulo dispone de dos botones Ejecutar en Colab (Figura 1), que dirigen a entornos complementarios:

  1. Parte Teórica, ubicada al inicio de cada capítulo, que contiene los conceptos presentados y ejemplos de código ejecutables;
  2. Parte Práctica, en la sección Parte Práctica con Ejercicios de Programación (EPs), dedicada a los ejercicios y a sus simuladores interactivos.

Figura 1: Botón clicable Ejecutar en Colab, disponible al inicio de las partes Teórica y Práctica de cada capítulo, que permite la ejecución interactiva de los ejemplos y ejercicios. En la versión PDF, existe un enlace HTML directo entre la imagen del simulador y su leyenda.

La generación de los notebooks está totalmente automatizada mediante el script gerar_notebooks_alunos.py, que adapta el contenido a entornos interactivos, permitiendo su ejecución sin necesidad de instalar Quarto.

Uso de herramientas de Inteligencia Artificial

La concepción, el proyecto pedagógico, la estructura conceptual y el contenido fundamental de este libro son de autoría exclusiva del autor.

En el proceso de edición y apoyo al desarrollo, se utilizaron, en sus versiones gratuitas, herramientas de Inteligencia Artificial (IA), como ChatGPT, Claude, DeepSeek y Gemini, empleadas estrictamente como recursos auxiliares. Su uso se limitó al apoyo en la revisión y mejora del estilo textual, a la optimización de la sintaxis de códigos y a la generación asistida de ilustraciones conceptuales y ejemplos.

Todas las respuestas y contenidos sugeridos por estas herramientas fueron sometidos a análisis crítico, verificación, validación técnica, adaptación e integración por parte del autor, quien asume la responsabilidad por el texto, los códigos y los recursos pedagógicos presentados. Las herramientas de IA no se consideran autoras ni coautoras de la obra, ni responsables de las decisiones intelectuales, técnicas o pedagógicas que fundamentan su contenido.

Se destaca, además, que los simuladores y recursos interactivos presentes en el libro —disponibles en las versiones HTML y Jupyter Notebook (IPYNB)— fueron diseñados e implementados como parte del enfoque pedagógico de la obra, con el objetivo de proporcionar experimentación directa de los conceptos presentados y favorecer la autonomía de aprendizaje del lector.

A diferencia del uso editorial descrito anteriormente, el pipeline de generación multilingüe (ver “Cómo se produce este libro”) emplea un modelo de lenguaje como componente de ingeniería del sistema: la traducción automática del contenido entre portugués y otros idiomas, con caché incremental que evita retraducir fragmentos sin cambios. Esta etapa utiliza la API de pago de DeepSeek (modelo deepseek-v4-flash); el libro completo ya ha sido traducido del portugués al inglés, al francés, al español y al italiano, y los Capítulos 1 a 5 cuentan además con una ruta en C++ que compila y ejecuta de verdad — a un costo acumulado del orden de unos pocos dólares, gracias a la caché incremental.

La biblioteca morph.py

La biblioteca morph.py (Zampirolli et al., 2025) acompaña toda la obra como una herramienta de apoyo a la enseñanza. Su objetivo no es sustituir bibliotecas consolidadas, como OpenCV, scikit-image, scikit-learn, NumPy o Matplotlib, ni competir con ellas en rendimiento o alcance. En cambio, busca hacer transparentes los algoritmos fundamentales de Procesamiento Digital de Imágenes y Visión Computacional (PDI-VC), permitiendo que el estudiante comprenda su implementación, modifique el código y desarrolle nuevas funcionalidades.

Siempre que sea posible, la biblioteca ofrece dos versiones para un mismo algoritmo: una implementación didáctica, escrita paso a paso para reflejar directamente las definiciones matemáticas presentadas en el libro, y otra implementación optimizada, basada en bibliotecas especializadas para aplicaciones prácticas.

NotaHerencia Técnica

La estructura de morph.py tiene como base herramientas de Morfología Matemática desarrolladas en Brasil, como MMachLib (Lotufo et al., 1997) y MMach (Barrera et al., 1998), además de la mmorph, utilizada en la obra de Dougherty; Lotufo (2003).. Estas bibliotecas sirvieron de referencia para la enseñanza del área durante décadas.

Esta filosofía puede observarse, por ejemplo, en los operadores morfológicos de dilatación:

  • mm.dil: implementación optimizada, indicada para aplicaciones prácticas;
  • mm.dil0: implementación didáctica de la dilatación para elementos estructurantes planares, siguiendo directamente la definición clásica de la Morfología Matemática;
  • mm.dil1: implementación didáctica de la dilatación para funciones estructurantes (kernels no planares), siguiendo rigurosamente su formulación matemática.

La biblioteca también ofrece funciones para lectura, visualización, conversión de colores, filtrado y morfología matemática a través de una interfaz simple:

from morph import mm

img = mm.gray(mm.read("lena.jpg"))  # lectura y conversión a niveles de gris
grad = mm.gradm(img)                # gradiente morfológico
mm.show(grad)                       # visualización

A lo largo del libro, se introducen nuevos métodos en la biblioteca para simplificar la realización de los Ejercicios de Programación (EPs). Entre ellos están mm.readTrain() y mm.readTest(), que automatizan la lectura de las bases de entrenamiento y prueba utilizadas en los capítulos dedicados al reconocimiento de patrones.

Además, todos los proyectos del Gemini Notebook incluyen el archivo morph.py, permitiendo consultar y discutir directamente la implementación de los algoritmos presentados en el libro. De esta forma, el estudiante puede utilizar el propio Gemini Notebook como un asistente de estudios, haciendo preguntas como:

Explique cómo se implementó el algoritmo mm.knn0 de morph.py, mostrando el código y comentando cada etapa de forma didáctica. Además, explique las diferencias entre mm.knn0() y mm.knn().

ImportanteImplementaciones didácticas e implementaciones optimizadas

En varios capítulos, un mismo algoritmo se presenta en dos versiones. Las funciones con sufijo 0, 1, etc. (por ejemplo, mm.knn0(), mm.dil0() y mm.dil1()) son implementaciones didácticas, desarrolladas para facilitar la comprensión de los algoritmos. En cambio, las funciones sin sufijo (como mm.knn() y mm.dil()) utilizan implementaciones optimizadas, frecuentemente basadas en bibliotecas especializadas, como OpenCV, scikit-image y scikit-learn, siendo más adecuadas para aplicaciones prácticas.

En las actividades evaluadas por el VPL de Moodle, bibliotecas como scikit-learn y, en algunos casos, scikit-image, pueden no ser utilizadas debido a las limitaciones de memoria del entorno de ejecución. Por este motivo, los Ejercicios de Programación (EPs) emplean preferentemente las implementaciones didácticas de morph.py, que producen los mismos resultados, aunque con menor rendimiento computacional. Esta restricción no existe cuando los programas se ejecutan localmente, por ejemplo, en VS Code, Jupyter Notebook o Google Colab.

El código fuente de la biblioteca está disponible en:

https://github.com/fzampirolli/pdi-vc/tree/master/morph

Ejercicios de Programación (EPs) y Validación Automática

Cada unidad del libro incluye Ejercicios de Programación (EPs) prácticos y de complejidad creciente, diseñados para consolidar los conceptos presentados a lo largo del capítulo. Cada EP está acompañado por un simulador interactivo, disponible en las versiones HTML e IPYNB, que permite al estudiante manipular parámetros, visualizar el comportamiento de los algoritmos y desarrollar una comprensión intuitiva del problema antes de iniciar su implementación. De esta forma, el proceso de aprendizaje combina experimentación, programación y validación automática.

La validación de las soluciones se realiza localmente mediante la clase TestSuite (testsuite.py), que compara la salida del programa con los archivos de casos de prueba (.cases):

TestSuite("EP01_01.py").run()

El sistema soporta múltiples lenguajes (Python, Java, C++, C, JavaScript y R) y puede integrarse directamente en Moodle. Para docentes interesados en el paso a paso completo de publicación de los EPs como actividades VPL, consulte el Guía del Profesor, al final de este prefacio, y el Apéndice B.

Código abierto

El proyecto se rige por principios de código abierto. El repositorio público reúne el texto, los códigos, las imágenes y los scripts: github.com/fzampirolli/pdi-vc

Cada versión del libro se archiva permanentemente en Zenodo con un DOI citable. Para citar este material en trabajos académicos:

ZAMPIROLLI, Francisco de Assis. PDI+VC — Procesamiento Digital de Imágenes y Visión Computacional. UFABC, 2026. DOI: 10.5281/zenodo.20784605

Cabe registrar, al respecto, que el contenido expuesto en esta obra refleja la mirada crítica, la propuesta pedagógica y la experiencia docente de su autor. Así, los análisis, enfoques y opiniones expresados a lo largo de este libro representan únicamente el entendimiento de su creador, no constituyendo ni reflejando un posicionamiento oficial o institucional de la Universidad Federal del ABC (UFABC).

Antes de comenzar: Notebooks en Python

El concepto de Literate Programming (Programación Literaria), propuesto por Donald Knuth (Knuth, 1984), fundamenta la estructura de este material. La lógica invierte el paradigma tradicional: el programa se escribe para la lectura humana, asemejándose a un ensayo, mientras que el código se extrae por separado para la ejecución computacional.

El contenido está estructurado en notebooks — documentos que intercalan células de texto (en Markdown) y células de código (en Python).

  • Ejecución: las células de código se identifican con [ ]. La ejecución puede realizarse con Shift + Enter o mediante el botón ▶️ de la interfaz.
  • Entornos: los notebooks pueden ejecutarse localmente, mediante Jupyter o Visual Studio Code (VS Code), así como en entornos de nube, como Google Colab.
TipNota sobre el formato

En entornos interactivos, el código puede modificarse y ejecutarse. En las versiones estáticas (HTML o PDF), los bloques de código tienen finalidad de lectura y referencia, sin perjuicio de la integridad de las explicaciones.


Guía del Profesor: Publicación de EPs en Moodle

Esta sección está destinada a docentes que deseen integrar los Ejercicios de Programación (EPs) a las actividades VPL (Virtual Programming Lab) de Moodle, complementando el Apéndice B.

Integración con Moodle (VPL)

Los EPs de los notebooks pueden convertirse en actividades VPL en Moodle. El script ep_tools.py (ejecutado mediante make build) automatiza la exportación de los EPs del final de cada capítulo en dos etapas:

  1. Extracción (make eps): genera un HTML interactivo independiente por EP, con enunciado, ejemplos y simulador, en gen/book/eps/<versao>/. Vea la lista completa en: https://fzampirolli.github.io/pdi-vc/eps/py.pt/index.html
  2. Conversión (make moodle): transforma el HTML en un fragmento autocontenido, sin dependencia de CSS externo, listo para pegarse en el editor de Moodle, en gen/book/eps/<versao>_moodle/. Vea un ejemplo en: https://fzampirolli.github.io/pdi-vc/eps/py.pt_moodle/EP01_01.html

Adicionalmente, todos los simuladores interactivos desarrollados a lo largo del libro pueden accederse directamente en https://fzampirolli.github.io/pdi-vc/simuladores/py.pt/.

NotaOtras rutas e idiomas

Los enlaces anteriores usan py.pt como ejemplo. Para acceder a los EPs o simuladores de otra combinación lenguaje/idioma, basta con cambiar ese segmento en la URL — por ejemplo, cpp.it para la ruta C++ en italiano: https://fzampirolli.github.io/pdi-vc/eps/cpp.it/index.html. La estructura es la misma para todas las combinaciones disponibles, en /eps/<versión>/, /eps/<versión>_moodle/ y /simuladores/<versión>/.

Al publicar con make publish, estas dos versiones de cada EP quedan disponibles en los enlaces indicados. El profesor puede combinar las dos estrategias: pegar la versión Moodle en el editor VPL (con simulador funcional) e incluir en el enunciado un enlace a la versión completa, donde las fórmulas se renderizan correctamente mediante MathJax.

AdvertenciaRevisión obligatoria antes de publicar en Moodle

Aunque automatizada, la conversión exige revisión del profesor debido a las limitaciones del editor TinyMCE/HTML Purifier de Moodle:

  • Fórmulas matemáticas — TinyMCE descarta barras invertidas (\), corrompiendo ecuaciones LaTeX. Por ello, la versión Moodle convierte fórmulas simples a HTML puro (entidades como &ge;, &times;). Las fórmulas complejas (\begin{cases}, matrices, integrales) pueden salir incompletas — revise y, si es necesario, reescríbalas en texto o indique la versión completa mediante enlace.
  • Figuras externas — Las imágenes complementarias deben insertarse manualmente en la actividad VPL.
  • Simuladores — Funcionan perfectamente siempre que utilicen JavaScript estándar con estilos inline y manipulación directa del DOM (getElementById). Atención: si incluye fórmulas en LaTeX que contengan el carácter \ en Moodle, los simuladores pueden dejar de funcionar.

Cómo Publicar en Moodle

  1. Acceda a la versión Moodle del EP deseado:

    https://fzampirolli.github.io/pdi-vc/eps/py.pt_moodle/EPXX_YY.html
  2. Copie el código fuente completo de la página (Ctrl+U → Ctrl+A → Ctrl+C).

  3. En Moodle, cree la actividad VPL, acceda al editor HTML, pegue el contenido (Ctrl+V) y guarde.

  4. Importe los archivos .cases de la carpeta all/capXX/casos/ en las configuraciones de pruebas del VPL.

TipReutilización de los Casos de Prueba

Los archivos .cases son compatibles con el VPL, permitiendo usar el mismo conjunto de pruebas tanto en el desarrollo local como en la corrección automatizada en Moodle.