Inteligencia Artificial

Analizando código con Codeium. Una IA para desarrolladores 

Introducción: 

Antes de trabajar con esta herramienta Codeium, es importante conocer un poco más sobre ella y así poder tener claro sus limitaciones, sus pros y contras después de todo no existe algo perfecto, y puede llegar a suceder que la funcionalidad que estabas esperando al momento de usarlo no esté disponible o que directamente no exista. 

Codeium es una herramienta de inteligencia artificial creada para ayudar a los desarrolladores en la programación. Proporciona autocompletado de código, sugerencias y asistencia en tiempo real mientras se escribe, lo que puede mejorar la productividad y facilitar la escritura de código. Funciona con múltiples lenguajes de programación y puede integrarse con varios entornos de desarrollo, lo que la convierte en un recurso útil para programadores de todos los niveles. Por esto es que en foros de internet a esta herramienta se le conoce como el GitHub-Copilot gratuito. 

Codeium ofrece un modelo freemium, lo que significa que tiene una versión gratuita con funcionalidades básicas, pero también opciones de pago que desbloquean características adicionales o capacidades avanzadas. Este modelo freemiun es el que usaremos más adelante. 

En cuanto a los modelos de IA que utiliza, Codeium se basa en modelos de Deep-Learning  que han sido entrenados en grandes cantidades de datos de código para proporcionar sugerencias relevantes y precisas. Pero desafortunada mente, los detalles específicos sobre los modelos utilizados pueden variar dependiendo de donde mires y no siempre están públicamente disponibles. 

Codeium soporta una amplia gama de lenguajes de programación y entornos de desarrollo, entre estos podemos ver que soporta JavaScript, TypeScript, Java, Kotlin, Go, Rust, Python y muchos más. En cuato a los entornos de desarrollo podemos ver que tiene compatibilidad con: 

Esto hace que sea una herramienta muy versátil para muchos proyectos. 

Web Reactiva by Dani. (2023, 27 septiembre). Codeium: Alternativa GRATIS a Github Copilot 🤖 #ia #programación [Vídeo]. YouTube. https://www.youtube.com/watch?v=5LF-Pwmfo5U

Tutorial

Lo que haremos será usar esta herramienta para pedirle que no explique a detalle el funcionamiento de un código, más específicamente de un Tetris hecho en Python. Este lo he sacado de un repositorio público en GitHub al final del articulo podrán encontrar el enlace que los llevará al repositorio. 

Requisitos previos:  

Antes de empezar debemos te asegurarnos de cumplir con los siguientes requisitos especialmente los de conocimiento del lenguaje de programación, pues este articulo no pretende enseñarte a programar, solo es una guía de cómo puedes llegar a usar la herramienta Codeium

  1. Conocimientos Previos
    • Conocimiento básico del lenguaje Python: Es fundamental para poder seguir la guía. 
  2. Herramientas y Entornos de Desarrollo:
    •  Tener instalado el IDE VScode (Visual Studio Code): Este es el entorno en el que se trabajará. 
    • Extensiones necesarias para VScode
  3. Instalación de Python 
    • Tener instalado Python: Nosotros usaremos la versión 3.10.11. 
    • Dependencias o paquetes necesarios: 
      • Pip 
      • Pygame 
      • Random 
  4. Cuentas y Accesos:

Paso 1: 

Cuenta de Codeium

Hacer este paso es fundamental para poder usar Codeium. Para ello no dirigimos a la siguiente dirección web:  https://codeium.com/account/login Aquí podremos crear una cuenta usando cualquier correo electrónico o ingresar directamente con Google

Paso2: 

Ahora nos dirigiremos a nuestro entorno de desarrollo VScode, allí instalaremos la extensión Codeium.

Una vez instalada notaremos una notificación que no pide autenticación. Para ello deberemos ingresar al siguiente enlace  https://codeium.com/show-auth-token e iniciar sesión con nuestra cuenta ya creada. 

Allí podremos ver que hay un token el cual es nuestra llave de autenticación por lo que no deberemos compartirlo con nadie. Copiaremos ese token y lo pegaremos en la línea de comandos del VScode junto con el siguiente comando: 

Codeium: Provide Authentication Token 

Pulsamos enter y luego pegamos nuestro token.

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c

Este token fue extraído de la página principal de JWT como un ejemplo de lo que usted debería ver en pantalla. 

Una vez hallamos hecho este paso podremos usar la IA. Esta herramienta tiene características muy útiles para el día a día como: autocompletado inteligente, sugerencias, corrección de errores y la que usaremos aquí, análisis y explicación del código.

Paso 3: 

Para que la IA nos pueda explicar un código es importante tenerlo, para ello usaremos el siguiente código: 

import pygame
import random

colors = [
    (0, 0, 0),
    (120, 37, 179),
    (100, 179, 179),
    (80, 34, 22),
    (80, 134, 22),
    (180, 34, 22),
    (180, 34, 122),
]


class Figure:
    x = 0
    y = 0

    figures = [
        [[1, 5, 9, 13], [4, 5, 6, 7]],
        [[4, 5, 9, 10], [2, 6, 5, 9]],
        [[6, 7, 9, 10], [1, 5, 6, 10]],
        [[1, 2, 5, 9], [0, 4, 5, 6], [1, 5, 9, 8], [4, 5, 6, 10]],
        [[1, 2, 6, 10], [5, 6, 7, 9], [2, 6, 10, 11], [3, 5, 6, 7]],
        [[1, 4, 5, 6], [1, 4, 5, 9], [4, 5, 6, 9], [1, 5, 6, 9]],
        [[1, 2, 5, 6]],
    ]

    def __init__(self, x, y):
        self.x = x
        self.y = y
        self.type = random.randint(0, len(self.figures) - 1)
        self.color = random.randint(1, len(colors) - 1)
        self.rotation = 0

    def image(self):
        return self.figures[self.type][self.rotation]

    def rotate(self):
        self.rotation = (self.rotation + 1) % len(self.figures[self.type])


class Tetris:
    def __init__(self, height, width):
        self.level = 2
        self.score = 0
        self.state = "start"
        self.field = []
        self.height = 0
        self.width = 0
        self.x = 100
        self.y = 60
        self.zoom = 20
        self.figure = None
    
        self.height = height
        self.width = width
        self.field = []
        self.score = 0
        self.state = "start"
        for i in range(height):
            new_line = []
            for j in range(width):
                new_line.append(0)
            self.field.append(new_line)

    def new_figure(self):
        self.figure = Figure(3, 0)

    def intersects(self):
        intersection = False
        for i in range(4):
            for j in range(4):
                if i * 4 + j in self.figure.image():
                    if i + self.figure.y > self.height - 1 or \
                            j + self.figure.x > self.width - 1 or \
                            j + self.figure.x < 0 or \
                            self.field[i + self.figure.y][j + self.figure.x] > 0:
                        intersection = True
        return intersection

    def break_lines(self):
        lines = 0
        for i in range(1, self.height):
            zeros = 0
            for j in range(self.width):
                if self.field[i][j] == 0:
                    zeros += 1
            if zeros == 0:
                lines += 1
                for i1 in range(i, 1, -1):
                    for j in range(self.width):
                        self.field[i1][j] = self.field[i1 - 1][j]
        self.score += lines ** 2

    def go_space(self):
        while not self.intersects():
            self.figure.y += 1
        self.figure.y -= 1
        self.freeze()

    def go_down(self):
        self.figure.y += 1
        if self.intersects():
            self.figure.y -= 1
            self.freeze()

    def freeze(self):
        for i in range(4):
            for j in range(4):
                if i * 4 + j in self.figure.image():
                    self.field[i + self.figure.y][j + self.figure.x] = self.figure.color
        self.break_lines()
        self.new_figure()
        if self.intersects():
            self.state = "gameover"

    def go_side(self, dx):
        old_x = self.figure.x
        self.figure.x += dx
        if self.intersects():
            self.figure.x = old_x

    def rotate(self):
        old_rotation = self.figure.rotation
        self.figure.rotate()
        if self.intersects():
            self.figure.rotation = old_rotation


# Initialize the game engine
pygame.init()

# Define some colors
BLACK = (0, 0, 0)
WHITE = (255, 255, 255)
GRAY = (128, 128, 128)

size = (400, 500)
screen = pygame.display.set_mode(size)

pygame.display.set_caption("Tetris")

# Loop until the user clicks the close button.
done = False
clock = pygame.time.Clock()
fps = 25
game = Tetris(20, 10)
counter = 0

pressing_down = False

while not done:
    if game.figure is None:
        game.new_figure()
    counter += 1
    if counter > 100000:
        counter = 0

    if counter % (fps // game.level // 2) == 0 or pressing_down:
        if game.state == "start":
            game.go_down()

    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            done = True
        if event.type == pygame.KEYDOWN:
            if event.key == pygame.K_UP:
                game.rotate()
            if event.key == pygame.K_DOWN:
                pressing_down = True
            if event.key == pygame.K_LEFT:
                game.go_side(-1)
            if event.key == pygame.K_RIGHT:
                game.go_side(1)
            if event.key == pygame.K_SPACE:
                game.go_space()
            if event.key == pygame.K_ESCAPE:
                game.__init__(20, 10)

    if event.type == pygame.KEYUP:
            if event.key == pygame.K_DOWN:
                pressing_down = False

    screen.fill(WHITE)

    for i in range(game.height):
        for j in range(game.width):
            pygame.draw.rect(screen, GRAY, [game.x + game.zoom * j, game.y + game.zoom * i, game.zoom, game.zoom], 1)
            if game.field[i][j] > 0:
                pygame.draw.rect(screen, colors[game.field[i][j]],
                                 [game.x + game.zoom * j + 1, game.y + game.zoom * i + 1, game.zoom - 2, game.zoom - 1])

    if game.figure is not None:
        for i in range(4):
            for j in range(4):
                p = i * 4 + j
                if p in game.figure.image():
                    pygame.draw.rect(screen, colors[game.figure.color],
                                     [game.x + game.zoom * (j + game.figure.x) + 1,
                                      game.y + game.zoom * (i + game.figure.y) + 1,
                                      game.zoom - 2, game.zoom - 2])

    font = pygame.font.SysFont('Calibri', 25, True, False)
    font1 = pygame.font.SysFont('Calibri', 65, True, False)
    text = font.render("Score: " + str(game.score), True, BLACK)
    text_game_over = font1.render("Game Over", True, (255, 125, 0))
    text_game_over1 = font1.render("Press ESC", True, (255, 215, 0))

    screen.blit(text, [0, 0])
    if game.state == "gameover":
        screen.blit(text_game_over, [20, 200])
        screen.blit(text_game_over1, [25, 265])

    pygame.display.flip()
    clock.tick(fps)

pygame.quit()

Como mencionamos anteriormente este código fue extraído de un repositorio público de GitHub. 

Luego una vez copiado el código, crearemos un nuevo archivo de Python y pegaremos allí el código, este archivo lo guardaremos con el nombre de “tetris.py”. 

Paso 4: 

Con nuestro archivo ya creado procederemos a abrirlo usando nuestro VScode

Una vez lo tengamos abierto seleccionaremos la primera parte del código, luego le daremos a clic derecho y escogeremos la opción, Codeium: Explain Selected Code Block. 

Podremos ver como a nuestro lado izquierdo se abre una pestaña de chat, allí Codeium nos dará una explicación de lo que hace el código seleccionado. Como es una IA y las cosas generadas por IA no son perfectas puede que la explicación proporcionada no sea muy adecuada o muy clara, en estos casos podemos volver a hacer el proceso para generar una respuesta que nos agrade más. 

La respuesta fue:

Este código define una clase llamada Figure que parece representar una figura geométrica en un espacio 2D. Aquí te explico lo que hace cada parte del código: 

Atributos de clase 

  • x y y son atributos de clase que se inicializan en 0. Estos parecen representar la posición de la figura en el espacio 2D. 
  • figures es una lista de listas que contiene definiciones de figuras geométricas. Cada figura se define como una lista de coordenadas x e y que forman la figura. 

Método __init__ 

  • El método __init__ es el constructor de la clase. Se llama cuando se crea un objeto de la clase Figure. 
  • El constructor toma dos parámetros, x e y, que se utilizan para inicializar la posición de la figura. 
  • El constructor también inicializa otros atributos: 
  • type: un número entero aleatorio entre 0 y el número de figuras definidas en la lista figures. Esto parece seleccionar una figura aleatoria de la lista. 
  • color: un número entero aleatorio entre 1 y el número de colores definidos en una lista llamada colors (que no se muestra en este código). Esto parece seleccionar un color aleatorio para la figura. 
  • rotation: se inicializa en 0. Esto parece representar la rotación de la figura. 

Método image 

  • El método image devuelve la definición de la figura actual, que se selecciona según el atributo type y la rotación actual (rotation). 

Método rotate 

  • El método rotate cambia la rotación de la figura. La rotación se incrementa en 1 y se mantiene dentro del rango de rotaciones posibles para la figura actual (es decir, el número de elementos en la lista figures[self.type]). 

En resumen, esta clase parece ser utilizada para crear objetos que representan figuras geométricas en un espacio 2D, con atributos como posición, tipo, color y rotación. Los métodos permiten obtener la definición de la figura actual y rotarla. 

Luego tenemos le pedimos que nos explique el código de la clase Tetris y obtenemos esto: 

Este código define una clase Tetris que representa un juego de Tetris. La clase tiene métodos para gestionar el estado del juego, incluyendo: 

  • Inicializar el juego con un alto y ancho dados 
  • Crear una nueva figura (tetromino) en la parte superior de la pantalla 
  • Comprobar si la figura actual intersecta con el campo de juego existente 
  • Romper líneas completas en el campo de juego y actualizar la puntuación 
  • Mover la figura hacia abajo, hacia los lados o rotarla 
  • Congelar la figura en su lugar cuando intersecta con el campo de juego 

El estado del juego se representa mediante una lista 2D field donde cada elemento es 0 (vacío) o un valor de color (ocupado por una figura). El atributo figure representa la figura actual, y su posición y rotación se actualizan mediante la lógica del juego. 

Y repetimos para la parte faltante del código. 

Este fragmento de código es el bucle principal del juego Tetris implementado utilizando la biblioteca Pygame. 

Aquí tienes una explicación breve: 

  1. El juego inicializa Pygame, define algunos colores y crea una ventana de juego de tamaño 400×500. 
  1. El bucle del juego se ejecuta hasta que el usuario cierra la ventana. 
  1. Dentro del bucle, el juego verifica los eventos (por ejemplo, pulsaciones de teclas, cierre de la ventana). 
  1. Basándose en los eventos, el juego actualiza su estado (por ejemplo, mueve la figura actual hacia abajo, la gira o la mueve a la izquierda o derecha). 
  1. El juego vuelve a dibujar la pantalla, incluyendo la cuadrícula del juego, la figura actual y la puntuación. 
  1. Si el juego ha terminado, muestra un mensaje “Game Over” y espera a que el usuario presione la tecla ESC para reiniciar el juego. 
  1. El bucle del juego se ejecuta a una tasa de fotogramas fija (25 FPS) para controlar la velocidad del juego. 

En resumen, este fragmento de código se encarga de manejar la entrada del usuario, actualizar el estado del juego y renderizar las gráficas del juego. 

Conclusión:

El uso de este tipo de herramientas puede ser muy útil para el ámbito laboral ya que les permite a los desarrolladores ahorrar tiempo y ser más eficientes. También en lo académico puede ser útil para quienes están aprendiendo programación, pero tienen dificultades en el entendimiento. 

Créditos: 

Autor: Juan Pablo Rojas Cardozo.

Editor: Mg.  Carlos Iván Pinzón Romero.

Código: UCPI1G1-2

Universidad: Universidad CentralFacultad de Ingeniería y Ciencias Básicas.

Codeium Free AI Code Completion & Chat.(s.f). Provide Authentication Token to VSCode. Codeium. https://codeium.com/show-auth-token

timurbakibayev. (s. f.). Tetris game in Python. github.com. https://gist.github.com/timurbakibayev/1f683d34487362b0f36280989c80960c