Indexación lógica y cartesiana en Julia

Julia , como la mayoría de los lenguajes informáticos técnicos, proporciona una implementación de array de primera clase con funciones muy importantes que facilitan el trabajo con arrays N-Dimensional. Una de las características más recientes, la transmisión basada en puntos (.) hace que la mayoría de las operaciones de array «repetitivas» sean un código de una sola línea.

Indexación de arrays

La indexación en arrays en Julia es similar a sus contrapartes.
Sintaxis:

x = array[índice_1, índice_2, …, índice_n]

donde cada index_k puede ser un entero escalar, una array de enteros o un objeto que representa una array de índices escalares.

La indexación de arrays en Julia es de dos tipos:

  • Indexación cartesiana
  • Indexación lógica

Indexación cartesiana

Las coordenadas cartesianas dan la ubicación de un punto en un plano 1D, 2D o 3D. Los índices cartesianos tienen un comportamiento similar. Dan el valor del elemento almacenado en una array 1D, 2D, 3D o nD.
Para los índices escalares , CartesianIndex{N}s , se comportan como una N-tupla de enteros que abarcan varias dimensiones, mientras que la array de índices escalares incluye arrays de CartesianIndex{N}
Sintaxis:

CartesianIndex(i, j, k...)   -> I
CartesianIndex((i, j, k...)) -> I

La sintaxis anterior crea un índice multidimensional I, que se puede usar para indexar una array multidimensional arr . Podemos decir que, arr[I] es equivalente a arr[i, j, k…] . Se permite mezclar índices enteros y cartesianos .
Ejemplo :

arr[Ipre, i, Ipost] 
(where Ipre and Ipost are CartesianIndex indices and i is an Int) 
can be a useful expression when writing algorithms that work along a single dimension
of an array of arbitrary dimensionality.

Indexación cartesiana escalar

Indexación cartesiana para arrays 1D:

# Create a 1D array of size 5
arr = reshape(Vector(1:2:10), (5))
  
# Select index number 1
arr[CartesianIndex(1)]
  
# Select index number 3
arr[CartesianIndex(3)]

Producción:

CartesianIndexing para una array 2D:

# Create a 2D array of size 3x2
arr = reshape(Vector(1:2:12), (3, 2))
  
# Select cartesian index 2, 2 
arr[CartesianIndex(2, 2)]
  
# Select index number 3, 1
arr[CartesianIndex(3, 1)]

Producción:

Indexación cartesiana para array 3D:

# Create a 3D array of size 2x1x2
arr = reshape(Vector(1:2:8), (2, 1, 2))
  
# Select cartesian index 1, 1, 1
arr[CartesianIndex(1, 1, 1)]
  
# Select index number 1, 1, 2
arr[CartesianIndex(1, 1, 2)]

Producción:

Indexación cartesiana para array nD:

# Create a 5D array of size 2x2x1x2x2
arr = reshape(Vector(1:2:32), (2, 2, 1, 2, 2))
  
# Select cartesian index 1, 2, 1, 2, 2
arr[CartesianIndex(2, 2, 1, 2, 2)]

Producción:

De los ejemplos anteriores, queda bastante claro que CartesianIndex simplemente reúne varios enteros en un objeto que representa un único índice multidimensional.
Habiendo discutido las representaciones escalares, hablemos de arrays de CartesianIndex{N} , que representan una colección de índices escalares, cada uno de los cuales abarca N dimensiones, dicha forma de indexación se conoce como indexación «puntual».

Indización cartesiana basada en array

Indización cartesiana basada en array para array 1D:

# Create a 1D array of size 5
arr = reshape(Vector(2:6), 5)
  
# Select an array of cartesian indices 2, 3, 5
arr[[CartesianIndex(2), 
     CartesianIndex(3), CartesianIndex(5)]]

Producción:

Indización cartesiana basada en array para array 2D:

# Create a 2D array of size 5x6
arr = reshape(Vector(1:30), (5, 6))
  
# Select an array of cartesian indices (5, 2), (3, 6), (1, 4)
arr[[CartesianIndex(5, 2), 
     CartesianIndex(3, 6), CartesianIndex(1, 4)]]

Producción:

Indización cartesiana basada en array para array 3D:

# Create a 3D array of size 2x3x1
arr = reshape(Vector(1:12), (2, 3, 2))
  
# Select an array of cartesian indices (1, 2, 1), (2, 2, 2), (1, 3, 1)
arr[[CartesianIndex(1, 2, 1),
     CartesianIndex(1, 3, 1), CartesianIndex(2, 2, 2)]]

Producción:

Indización cartesiana basada en array para array nD:

# Create a 5D array of size 2x2x1x2x2
arr = reshape(Vector(1:2:32), (2, 2, 1, 2, 2))
  
# Select an array of cartesian indices 
# (1, 2, 1, 1, 1), (1, 2, 1, 2, 2), (2, 1, 1, 2, 1)
arr[[CartesianIndex(1, 2, 1, 1, 1), 
     CartesianIndex(1, 2, 1, 2, 2), 
     CartesianIndex(2, 1, 1, 2, 1)]]

Producción:

Esto es realmente útil, en caso de que queramos seleccionar elementos específicos de una array si no están en orden. Pero qué pasa si tenemos una array de 1000 y necesitamos extraer 100 elementos, ¡será bastante tedioso!
Aquí es donde entra en juego la transmisión de puntos (.) .

# Create a 3D array of size 3x3x3
arr = reshape(Vector(1:27), (3, 3, 3))
  
# Select diagonal elements in all the 
# 3 planes of cartesian coordinates
arr[[CartesianIndex(1, 1, 1), CartesianIndex(2, 2, 1), 
     CartesianIndex(3, 3, 1), CartesianIndex(1, 1, 2), 
     CartesianIndex(2, 2, 2), CartesianIndex(3, 3, 2),
     CartesianIndex(1, 1, 3), CartesianIndex(2, 2, 3), 
     CartesianIndex(3, 3, 3)]]
  
# Using dot broadcasting and (:)colon, to reduce code
arr[CartesianIndex.(axes(arr, 1), axes(arr, 2), :)]

Resultado:

¡Cuán eficientemente hemos podido reducir nuestro código en el tercer paso!

¿Qué debemos hacer con la indexación cartesiana?
Observamos que los índices cartesianos se parecen mucho a las coordenadas cartesianas y funcionan de manera similar.
Ejemplo:

We have a 3D shape in space, and it is mapped out by storing the coordinates of it's 
edges in an array and we might want to mask out a region from the shape. It becomes 
easy to deal with by using CartesianIndices, since they resemble the coordinate system. 

Indexación lógica

En computación/electrónica, la base es una lógica de naturaleza determinista. Está:

true, false
one, zero
on, off

Es básicamente una selección de elementos en los índices donde los valores de nuestra array de indexación lógica son verdaderos.
Una array de indexación lógica se denomina » máscara «, ya que enmascara los valores que son falsos. Una máscara es de tipo bool (booleano).

Relación con la indexación cartesiana:

Indexing by a N-dimensional boolean array is equivalent to indexing by the vector 
of CartesianIndex{N}s where its values are true. 

Ejemplo: implementación de una máscara lógica

# Create a 2D array of size 5x5
arr = reshape(Vector(1:25), (5, 5))
  
# Apply a logical mask to the array
arr[[true, false, true, false, true], :]

Salida: Entonces vemos como solo se seleccionan

las filas cuyo índice coincide con el índice de verdaderos en nuestra máscara [verdadero, falso, verdadero, falso, verdadero] .

Cualquier condición que produzca un valor booleano se puede utilizar como máscara.
Ejemplo para array 1D:

# Create a 1D array of size 10
arr = reshape(Vector(4:2:22), 10)
  
# Create a power of 2 logic mask 
# and map it with the size of arr
mask = map(ispow2, arr)
  
# Apply it to the array
arr[mask]

Producción:

Ejemplo para array 2D:

# Create a 2D array of size 10x10
arr = reshape(Vector(1:100), (10, 10))
  
# Create a prime number logic mask and 
# map it with the size of arr 
# Julia library for working with prime numbers 
using Primes 
mask = map(isprime, arr)
  
# Apply it to the array
arr[mask]

Producción:

Ejemplo de array 3D:

# Create a 3D array of size 3x2x3
arr = reshape(Vector(2:19), (3, 2, 3))
  
# Create a prime number logic mask 
# and map it with the size of arr
# Julia library for working with prime numbers 
using Primes
mask = map(isprime, arr)
  
# Apply it to the array
arr[mask]

Producción:

Uno de los casos más utilizados de indexación lógica es cuando queremos filtrar elementos de una array en función de múltiples condiciones.
Ejemplo:

# Create a 3D array of size 3x2x3
arr = reshape(Vector(2:19), (3, 2, 3))
  
# Create a function that checks for 
# both prime number or power of two
# Julia library for working with prime numbers 
using Primes   
function prime_and_2pow(arr)
    if isprime(arr) || ispow2(arr)
        return true
    else 
        return false
    end
end
  
# Create a logic mask and map it
# with the size of arr
mask = map(prime_and_2pow, arr)
      
# Apply it to the array
arr[mask]

Producción:

Publicación traducida automáticamente

Artículo escrito por arsh_sharma y traducido por Barcelona Geeks. The original can be accessed here. Licence: CCBY-SA

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *