Santiago Quiñones Cuenca
Software Developer and Educator, Master in Software Engineering, Research UTPL {Loja, Ecuador} Repositories: http://github.com/lsantiago
Programación funcional y reactiva - Computación
Func. matemáticas hacia la programación funcional
Funciones matemáticas
Algo para recordar
Definición: Relación que asigna a cada elemento de entrada exactamente un elemento de salida
Propiedades:
Funciones matemáticas
Propiedades
Determinismo:
Transferencia referencial:
Sin efectos colaterales:
Del mundo matemático al mundo computacional
La pregunta clave: ¿Podemos programar de la misma manera que definimos funciones matemáticas?
La respuesta: Sí, y ese es el paradigma funcional.
Funciones matemáticas
Funciones matemáticas
Transformación de función matemática a código
def f(x: Int) = Math.pow(x, 2) + 1Funciones puras
Funciones puras
Definición
Una función pura es una función que:
Es la traducción directa de una función matemática al código.
Funciones puras
Ejemplos
Es pura porque:
def suma(a: Int, b: Int): Int = a + bEjemplo 1
Es pura porque:
def promedio(numeros: List[Int]): Double = {
  val suma = numeros.sum
  val cantidad = numeros.length
  suma.toDouble / cantidad
}Ejemplo 2
Funciones no puras
Ejemplos
No es pura porque:
contador
var contador = 0
def incrementarContador(x: Int): Int = {
  contador = contador + x  // ❌ Modifica estado externo
  contador
}Ejemplo 1: Depende de estado externo
Funciones no puras
Ejemplos
No es pura porque:
def leerArchivo(nombre: String): String = {
  scala.io.Source.fromFile(nombre).mkString  // ❌ I/O
}Ejemplo 2: Operaciones de I/O
Funciones puras
Antitesis
Funciones puras
Principales características
Funciones puras
Implementación en Scala
object Counter {
  // Función pura que incrementa un contador
  def incrementCounter(counter: Int): Int = {
    counter + 1
  }
  // Función pura que multiplica el contador
  def multiplyCounter(counter: Int, num: Int): Int = {
    counter * num
  }
  // Función pura que devuelve el valor del contador (en este caso innecesario porque el
  // no necesita una función, simplemente se usa directamente)
  def getCounter(counter: Int): Int = {
    counter
  }
}
// Uso de las funciones
val currentCounter = 5
val incremented = Counter.incrementCounter(currentCounter)
val multiplied = Counter.multiplyCounter(currentCounter, 2)
println(s"Incremented: $incremented")  // Imprimirá 6
println(s"Multiplied: $multiplied")    // Imprimirá 10Funciones vs Métodos
Trabajo en grupo
¿Cuándo es mejor usar funciones puras y cuándo métodos de objetos?
Debate de cada enfoque
Funciones puras vs Métodos (Leng. Prog.)
Diferencias conceptuales
Método en POO
Ejemplo
class Contador {
  private var valor: Int = 0  // Estado mutable
  
  def incrementar(): Unit = {  // Método
    valor += 1  // Modifica estado interno
  }
  
  def obtenerValor(): Int = valor
}
val c = new Contador()
c.incrementar()  // Primera llamada
c.obtenerValor()  // Devuelve 1
c.incrementar()  // Segunda llamada
c.obtenerValor()  // Devuelve 2 - ¡Resultado diferente!Funciones en programación funcional
Ejemplo
// No hay clase con estado
def incrementar(valor: Int): Int = valor + 1
val valor1 = 0
val valor2 = incrementar(valor1)  // 1
val valor3 = incrementar(valor2)  // 2
// Cada llamada es independiente
incrementar(5)  // Siempre devuelve 6
incrementar(5)  // Siempre devuelve 6Comparación directa
Lenguaje Scala
Tipos básicos
// Numéricos
val entero: Int = 42
val largo: Long = 42L
val flotante: Float = 3.14f
val doble: Double = 3.14159
// Booleano
val verdadero: Boolean = true
val falso: Boolean = false
// Caracter y String
val letra: Char = 'A'
val texto: String = "Hola mundo"
// Unit (equivalente a void)
val nada: Unit = ()Funciones
Definición básica
// Sintaxis completa
def nombreFuncion(parametro1: Tipo1, parametro2: Tipo2): TipoRetorno = {
  // cuerpo de la función
  resultado
}
// Ejemplo
def suma(a: Int, b: Int): Int = {
  a + b
}
// Si el cuerpo es una sola expresión, se pueden omitir las llaves
def suma2(a: Int, b: Int): Int = a + b
// Scala infiere el tipo de retorno (pero es buena práctica especificarlo)
def suma3(a: Int, b: Int) = a + bFunciones
Funciones anónimas (lambdas)
// Sintaxis completa
val sumar = (a: Int, b: Int) => a + b
// Uso
sumar(3, 4)  // 7
// Con un solo parámetro
val cuadrado = (x: Int) => x * x
cuadrado(5)  // 25
// Sintaxis abreviada con placeholder
val doble: Int => Int = _ * 2
doble(5)  // 10Otra forma de definir funciones
Los métodos también pueden tener expresiones de varias líneas.
def dividir(a: Int, b: Int): Int = {
  val dividendo = a
  val divisor = b
  dividendo / divisor
}
dividir(2, 3)
La ultima expresión en el cuerpo del método es el valor de retorno del mismo. (Scala tiene una palabra reservada return, pero se usa raramente y no se aconseja usarla)
Otra forma de definir funciones
Los métodos también pueden tener expresiones de varias líneas.
def isAdult(age: Int): Boolean = {
  if (age >= 18) {
    true // La persona es mayor de edad
  } else {
    false // La persona es menor de edad
  }
}
Otra forma de definir funciones
Las funciones se pueden simplificar en una expresión
def isAdult(age: Int): Boolean = if (age >= 18) true else false
Otra forma de definir funciones
Se puede realizar operaciones con cadenas
def countWithoutOpenVowels(word : String) : Int = { 
   word.toLowerCase.replaceAll("a", "").replaceAll("e", "").replaceAll("o", "").length
}Funciones matemáticas a código
Funciones matemáticas básicas
Implementar las siguientes funciones
f(x) = 2x + 3g(x) = x²h(x) = √x(g ∘ f)(x)
Funciones matemáticas
El paradigma de la Programación Funcional (FP) se fundamenta en una premisa simple pero de gran alcance: construir programas utilizando exclusivamente funciones puras. En esencia, la FP es una disciplina que lleva lo que muchos consideran buenas prácticas de programación hasta su punto lógico
Funciones matemáticas
Traducción matemática en código
Funciones matemáticas a código. Expresiones
Funciones matemáticas a código.
Funciones matemáticas a código.
Definir función que tome un entero n y calcule el factorial de n
Funciones matemáticas a código.
Definir función que tome un entero n y calcule el factorial de n
Otra casos de funciones matemáticas
Traducción matemática en código
def g(n: Int) = (1 to n).map(k => k*k).sumOtra casos de funciones matemáticas
Traducción matemática en código
def g(n: Int): Double = math.pow((1 to n).product, 3) + (2* math.pow(n, 1.0/n))Trabajo de consulta
Trabajo de consulta
¿Qué son las funciones anónimas?
By Santiago Quiñones Cuenca
Programación funcional - funciones
Software Developer and Educator, Master in Software Engineering, Research UTPL {Loja, Ecuador} Repositories: http://github.com/lsantiago