Você está na página 1de 77

IFTS 18

Introducción a C#

Ingeniería del Software

Programación Aplicada

Autor:
Ing. Gabriel Esquivel

Año:
2018
IFTS18 Introducción a C# 2018

Tabla de contenido
Introducción .................................................................................................................................. 5
Sistema Operativo ......................................................................................................................... 5
.Net Framework ............................................................................................................................ 8
Lenguaje Intermedio (IL) .................................................................................................................... 9
Task Manager - Process Explorer ..................................................................................................... 11
Tiempos de Desarrollo de una Aplicación ................................................................................... 13
Resumen.................................................................................................................................. 13
Concepción del Producto – Especificaciones y Alcance del Proyecto.............................................. 14
Pre/Re Diseño y Análisis: ................................................................................................................. 14
Design Time o Tiempo de Diseño ..................................................................................................... 16
Programming-Editing Time o Tiempo de Programación-Edición: ................................................... 18
Compilación ...................................................................................................................................... 19
Execution & Debugging Time o Tiempo de Ejecución y Depuración .............................................. 20
Quality Test o Verificación de Calidad ............................................................................................. 20
Clasificación de los Lenguajes ..................................................................................................... 21
Código de Maquina ................................................................................................................. 21
Programación de Bajo Nivel .................................................................................................... 21
Programación de Nivel Intermedio ......................................................................................... 22
Programación de Alto Nivel .................................................................................................... 23
Paradigmas de Programación ..................................................................................................... 25
Programación Estructurada u Orientada a Métodos .............................................................. 25
Funciones - Métodos ......................................................................................................................... 26
Programación Orientada a Eventos ........................................................................................ 29
Evento ............................................................................................................................................... 29
Entorno de Desarrollo ................................................................................................................. 31
Editor de Código ...................................................................................................................... 31
Diseñador/Editor de Formularios............................................................................................ 32
Proyectos y Soluciones ..................................................................................................................... 33
Panel Explorador de Soluciones ....................................................................................................... 33
Panel de Propiedades ........................................................................................................................ 34
Examinador de Objetos ..................................................................................................................... 35
Aplicaciones y Formularios.......................................................................................................... 37
Creación de un nuevo Proyecto .............................................................................................. 37
Programación Orientada Objetos ............................................................................................... 40
Concepto de Objeto ................................................................................................................ 40
Miembros de un objeto........................................................................................................... 41
Clases....................................................................................................................................... 41

Ing. Gabriel Esquivel 2


IFTS18 Introducción a C# 2018
Herencia ............................................................................................................................................ 41
Interfaces................................................................................................................................. 42
El Constructor ................................................................................................................................... 43
Clase no heredable – sealed .............................................................................................................. 45
Clases no instanciables – abstract .................................................................................................... 46
Clase estática – static ........................................................................................................................ 46
Reemplazo de Miembros en Clases Heredadas ...................................................................... 47
abstract, virtual y override ................................................................................................................ 47
abstract .............................................................................................................................................. 48
virtual ................................................................................................................................................ 48
Reemplazo de Métodos - override .................................................................................................... 49
Sombreado - new .............................................................................................................................. 50
Casteo ............................................................................................................................................... 50
Palabras Reservadas “this”, “base” ........................................................................................ 51
Variables Miembro o Campos .......................................................................................................... 52
Niveles de Acceso .................................................................................................................... 52
Métodos .................................................................................................................................. 52
Parámetros ........................................................................................................................................ 53
Parámetros pasados por Valor........................................................................................................... 53
Parámetros pasados por Referencia .................................................................................................. 54
Sobrecarga............................................................................................................................... 54
Sobrecarga de Métodos tradicional ................................................................................................... 55
Parámetros Opcionales...................................................................................................................... 55
Propiedades............................................................................................................................. 56
Propiedades tradicionales o CLR ...................................................................................................... 56
Read Only Property .......................................................................................................................... 57
Auto propiedades .............................................................................................................................. 57
Write Only Property.......................................................................................................................... 57
Delegados ................................................................................................................................ 58
Declaración de un Delegado ............................................................................................................. 59
Declaración de la variable Delegado................................................................................................. 60
Conclusión ........................................................................................................................................ 60
Eventos .................................................................................................................................... 61
Generación Eventos .......................................................................................................................... 62
Captura de Eventos ........................................................................................................................... 64
Controles Básicos ........................................................................................................................ 66
Inserción de Controles en un Formulario................................................................................ 66
Jerarquía de Herencia de los Controles .................................................................................. 68
Menús...................................................................................................................................... 69
Cuadros de dialogo .................................................................................................................. 70
Debug Programming o Execution Time Programming ............................................................ 71
Ejecución paso a paso ....................................................................................................................... 71
Puntos de Interrupción ...................................................................................................................... 72

Ing. Gabriel Esquivel 3


IFTS18 Introducción a C# 2018
Edición en tiempo de Depuración ..................................................................................................... 74
Revisión de los valores de las variables ............................................................................................ 74

Ing. Gabriel Esquivel 4


IFTS18 Introducción a C# 2018
Introducción
El desarrollo de una aplicación de media envergadura o profesional plantea la necesidad de
aprender o entender conceptos que a veces son dejados de lados en las materias informáticas
de nivel básico.
Por ejemplo, como está formado un sistema operativo (SO a partir de ahora) como Windows o
Linux, y como la aplicación interactúa con dicho SO es de suma importancia en éste tipo de
emprendimientos.
Otros conceptos necesarios que serán expuestos en las siguientes paginas son los siguientes:
 Tipos de Aplicaciones
 Tiempos de desarrollo
 Bibliotecas
 Herramientas de depuración
 Uso de bibliotecas de alto nivel

Sistema Operativo
Es un software complejo, formado por una gran cantidad y variedad de sub aplicaciones y
bibliotecas que se encargan de servir de soporte a las aplicaciones de alto nivel del usuario,
separando a estas de las diferencias entre los distintos hardwares disponibles en el mercado
moderno.
Un esquema simple de lo mencionado es el mostrado:
Figura 1. Capas de un Sistema Operativo

Aplicaciones del
Usuario Capa de
Aplicación
Servicios del Usuario Mayor Nivel de Privilegios

Software

Sistema
Operativo
Hardware

HardWare

Ing. Gabriel Esquivel 5


IFTS18 Introducción a C# 2018
Si profundizamos un poco más el modelo tenemos:
Figura 2. Detalles del Sistema Operativo

Aplicaciones del
Usuario Capa de
Aplicación
Servicios del Usuario

.Net Framework

Mayor Nivel de Privilegios


Servicios del
Sistema
Acceso

Software
directo a
Hardware
APIs de Windows Prohibido

Bibliotecas del Sistema


Sistema
Operativo
Kernel

HAL

Hardware
HardWare

Como se aprecia en la figura, el sistema operativo aísla al hardware de las aplicaciones del
usuario. Debido a ello, el usuario podrá correr sus programas habituales (Word, Excel, Corel,
etc.) despreocupándose de las sutilezas que a muy bajo nivel suceden.
Este esquema permite entonces que dichas aplicaciones corran prácticamente en cualquier PC
de escritorio o portátil.
La última capa del Sistema Operativo, el HAL (Hardware Abstraction Layer ó Capa de
Abstracción del Hardware en castellano) es la encargada de separar a su vez al núcleo del
sistema, denominado a menudo Kernel, de todas las posibles combinaciones de hardware
halladas en el mercado.
El Kernel es el encargado de las tareas básicas que hacen al funcionamiento del Sistema, tales
como el acceso a disco para la lectura y escritura de archivos, la administración de memoria,
etc.

Ing. Gabriel Esquivel 6


IFTS18 Introducción a C# 2018
Las bibliotecas del Sistema ofrecen una interfaz de interacción entre las aplicaciones de alto
nivel y el Kernel. A este conjunto de bibliotecas se las denomina APIs de Windows (Application
Program Interface), y en la práctica son el medio a través del cual las aplicaciones piden
recursos e interactúan con el Sistema Operativo.
Formando parte también del SO se encuentran un conjunto de aplicaciones que usualmente
no poseen interfaz grafica, las cuales se denominan Servicios de Windows, y junto al Kernel le
dan funcionalidad a todo el sistema. Ejemplos de estos servicios son: el Cliente de DNS, la cola
de impresión (spooler), el cliente DHCP, etc.
Finalmente, en la capa superior, y en general con un mínimo de privilegios se encuentran los
servicios y aplicaciones del usuario, los cuales a menudo interactúan con los servicios del
sistema o con el Kernel, pero a través de las APIs. Observe que, en un SO moderno, el acceso
directo a Hardware por parte de una aplicación de usuario está prohibido, cosa que no se daba
en SO antiguos, como el DOS.

Ing. Gabriel Esquivel 7


IFTS18 Introducción a C# 2018

.Net Framework
Así denominó Microsoft a su conjunto de bibliotecas que, por encima de cualquiera de sus
sistemas operativos Windows, dan soporte a la creación de potentes aplicaciones, servicios,
bibliotecas y páginas webs, entre otros tipos de proyectos.
En el siguiente gráfico se puede ver la estructura de capas del software que corre en una
computadora, y el lugar específico del .Net Framework en éste.
Figura 3. Estructura en capas de una aplicación .Net después de ser compilada

VB .Net C# VC ++ Otros
Código Fuente
.Net Lenguajes

Visual Studio
Aplicaciones
IDE
Compilación

Aplicación IL
Lenguaje
Intermedio
Biblioteca IL

.Net FrameWork MONO DotGNU Bibliotecas de


Alto Nivel

SO SO Linux, MAC, Windows, Sistema


Windows Otros Operativo

Como apreciará, a partir de una gran variedad de lenguajes, entre los que se destacan C# y
Visual Basic .Net, y con el uso de un software especializado denominado IDE (de Integrated
Development Environment, como el Visual Studio) es posible escribir código fuente, que tras
ser compilado, produce una aplicación y/o bibliotecas, las que basadas en las librerías de alto
nivel sistema, como el .Net Framework en Windows o Mono y DotGNU con Linux y MacOS
(entre otros sistemas operativos), permiten que estos corran o interactúen con el SO.

Ing. Gabriel Esquivel 8


IFTS18 Introducción a C# 2018
A su vez, el mismo .Net Framework tiene una estructura en capas, que ha sido concebida y
construida desde sus comienzos, allá por fines de los 90, para ser totalmente escalable y retro-
compatible, como se puede ver en el siguiente esquema:
Figura 4. Estructura en capas del Framework

PLINQ TPL

4.0
LINQ ADO .NET Entity

3.5
FrameWork

WPF WCF WF Card

3.0
Space

WinForms ASP .Net ADO .Net

.Net FrameWork 2.0


Base Class Library

Common Language Runtime

Como podrá apreciar, la estructura en capas que se ha planteado, desarrollando una sobre la
otra, permite crear un juego de bibliotecas realmente muy poderoso y funcional, comenzando
con el Framework 2.0 y llegando hasta el último 4.0.
Las bibliotecas más básicas, como las contenidas en el Framework 2.0 permiten desarrollar
aplicaciones muy potentes, pero con la tecnología disponible en el Windows Presentation
Foundation o WPF, las aplicaciones creadas pueden manifestar y mostrar efectos visuales
deslumbrantes y hasta sorprendentes, sin necesariamente complicar mucho el código fuente
producido.
Dado que los detalles de cada una de estas tecnologías son ampliamente bastos, salvo algunas
excepciones, se deja al lector investigar cada uno de ellos en función de sus propias
necesidades.

Lenguaje Intermedio (IL)


Las aplicaciones y bibliotecas generadas con estas tecnologías no son compiladas como es
costumbre a código de máquina, sino que se compilan a un código intermedio denominado
hoy en día Intermediate Language o IL.
Este código generado es común a cualquiera de los lenguajes de alto nivel del que
originalmente provienen. Debido a ello, el fantasma de la alta performance y velocidad de

Ing. Gabriel Esquivel 9


IFTS18 Introducción a C# 2018
ejecución del Visual C++ desaparece en el caso de los lenguajes .Net, ya que en principio todos
los lenguajes generan el mismo tipo de código IL.
Aún así, para mantener retro compatibilidad con versiones previas Visual Studio, es posible
generar aplicaciones de Visual C++ Win32, también denominadas nativas, la cual se compilan a
lenguaje de maquina en lugar de código IL, manteniendo las ventajas previamente
mencionadas. Para ilustrar esta situación, se muestra una variante de un grafico anterior:
Figura 5. Compilación y ejecución de código .Net y Nativo

VB .Net C# VC ++ Otros VC ++ Código


.Net Win32 Fuente

Compilación

Visual Studio
Aplicaciones
IDE

Aplicación Win32

Aplicación IL
Lenguaje
Compilación Intermedio
Biblioteca IL

.Net FrameWork Bibliotecas de


Alto Nivel

SO Sistema
Windows Operativo

Por supuesto, el microprocesador no corre código IL, y debido a ello, este debe ser
recompilado a código de máquina antes de que la aplicación se ejecute. Dicha aplicación en
código de maquina se mantiene en un cache salvo que una nueva versión o una diferente del
ejecutable se ejecute.
Esta metodología de trabajo es similar a la utilizada previamente por SUN Microsystems con su
lenguaje Java, su código intermedio denominado Java ByteCode, y su Java Virtual Machine.

Ing. Gabriel Esquivel 10


IFTS18 Introducción a C# 2018

Task Manager - Process Explorer


Una forma de visualizar lo mencionado es mediante una aplicación que viene incorporada con
el sistema operativo windows, y se hace visible por ejemplo presionando al mismo tiempo las
teclas Control Alt Del. Dicha aplicación nativa tiene el nombre de Task Manager. Sin embargo,
adolece de la falta de información vital a la hora mostrar todo lo posible sobre que se halla
corriendo en la PC.
Para suplir dicha deficiencia, SysInternal, una compañía ahora adquirida por Microsoft,
desarrolló un reemplazo del Task-Manager, al cual denominaron Process Explorer.
Una vista de este junto a algo de la información que provee se halla a continuación:
Figura 6. Vista típica del Process Explorer

Entre parte de la información suministrada por esta aplicación se encuentra:


 Estado de la aplicación (si corre normalmente, si se encuentra colgada)
 Consumo de recursos del microprocesador

Ing. Gabriel Esquivel 11


IFTS18 Introducción a C# 2018
 Uso de memoria
 Hilos de ejecución utilizados (Threads)
 Nombre y ubicación de las aplicaciones en el disco
Los usos básicos pueden ser:
 Determinar si una aplicacion corre correctamente
 Ver qué cantidad de recursos consume
 Identificar aplicaciones peligrosas, como virus y aplicaciones similares

Ing. Gabriel Esquivel 12


IFTS18 Introducción a C# 2018

Tiempos de Desarrollo de una Aplicación


Entendemos por tiempos de desarrollo a aquellos intervalos perfectamente definidos y
diferenciados durante los cuales se codifica e implementa el desarrollo de una aplicación.
Entre estos podemos distinguir:
 Concepción del Producto – Especificaciones y Alcance del Proyecto
 Pre/Re Diseño y Análisis:
 Design Time o Tiempo de Diseño
 Programming-Editing Time o Tiempo de Programación-Edición:
 Compilación
 Execution & Debugging Time o Tiempo de Ejecución y Depuración
 Quality Test o Verificación de Calidad

Resumen
Las diferentes etapas del diseño de una aplicación pueden apreciarse debajo:
Figura 7. Etapas de desarrollo de una aplicación

Rediseño Total Concepción -


Especificaciones

Desarrollo
Finalizado Pre/Re Diseño -
Relevamiento

Rediseño Parcial
Diseño de
Formularios
Chequeo de
Calidad

Programación
Errores de Errores de
ejecución Compilación

Ejecución y Compilación
Depuración

Como podrá ver, siempre hay ciclos donde se hacen correcciones, pero solo uno es desastroso,
y es aquel en el cual el diseño tiene que ser replanteado casi en su totalidad, produciendo
pérdidas considerables al desarrollo, generalmente en dinero y/o tiempo.

Ing. Gabriel Esquivel 13


IFTS18 Introducción a C# 2018
Concepción del Producto – Especificaciones y Alcance del Proyecto
Esta, usualmente está en manos de quienes quieren el producto para su venta, y se caracteriza
por la creación del producto en forma conceptual, comenzando con la idea, de que debe hacer
y cómo debe funcionar.
Es muy importante que estas ideas se plasmen en documentos que especifiquen con la mayor
cantidad de detalles los alcances y metas que se esperan del producto, evitando así malos
entendidos en el futuro.

Pre/Re Diseño y Análisis:


Es el periodo previo al desarrollo, durante el cual se analiza las formas más efectivas de
resolver el problema. En esta etapa en Programación Orientada a Objetos se suele utilizar
Diagramas de Flujo, de Casos de Uso, UML, de Clases y otros, los que permiten plantear un
esquema grafico de cómo los objetos interactúan entre sí y con los usuarios cuando se ejecute
el programa.
Un ejemplo de un pequeño diseño de software mediante diagramas de clases es el siguiente:
Figura 8. Diagrama de Clases

Interfaces Clase hija


Implementadas

Herencia

Clase Base

Métodos
Miembros

Ing. Gabriel Esquivel 14


IFTS18 Introducción a C# 2018
Como se aprecia en el grafico, aparecen las clases, junto con sus miembros (campos,
propiedades, métodos y eventos), las clases hijas, y el árbol de herencia, todo esto en teoría
sin escribir una sola línea de código.
En ésta etapa también debe hacerse el análisis de los tiempos involucrados en la
implementación de cada fase del proyecto, utilizando por ejemplo diagramas de Gantt y PERT
(Program Evaluation and Review Technique) u otros.
Tenga presente que, si evita o realiza mal esta etapa es muy probable que en un diseño de
envergadura deba hacer correcciones y replanteos en varias oportunidades, lo que degradara
apreciablemente el tiempo final que insume el desarrollo.
Debe tener bien claro que ésta etapa por lo general está a cargo de Ingenieros o Arquitectos
de Software, o personal idóneo, quienes en algún momento estudiaron y aplicaron este tipo
de herramientas y tecnologías.
En cuanto a los diagramas de tiempos, debajo en los siguientes gráficos aparece un diagrama
de Gantt para el desarrollo de una aplicación informática hipotética:
Figura 9. Árbol de tareas del Diagrama de Gantt

Ing. Gabriel Esquivel 15


IFTS18 Introducción a C# 2018
Esquema de Tiempos del Diagrama de Gantt:
Figura 10. Diagrama de Gantt

Como apreciará, los tiempos mínimos necesarios e inclusive algunos retrasos inesperados
pueden ser tenidos en cuenta aquí para poder cumplir con los plazos óptimos esperados.

Design Time o Tiempo de Diseño


Durante esta etapa por lo general se le da el formato visual a un formulario, un control o a una
página Web. Esta tarea involucra mucho del aspecto estético y decorativo de la aplicación, y
puede ser realizado por casi cualquier persona, inclusive aquellas que conocen poco o nada de
programación. Obviamente, en aplicaciones de gran magnitud es ideal que lo realice alguien
con experiencia en diseño grafico.

Ing. Gabriel Esquivel 16


IFTS18 Introducción a C# 2018
Por ejemplo, a continuación se muestra una porción del diseño de un formulario de WPF
(Windows Presentation Fundation), una de las últimas tecnologías del Framework para el
diseño de aplicaciones y páginas web orientadas a la presentación.
Figura 11. Vista Diseño de un formulario de WPF

Control

Control

Código
XAML

En la imagen se puede apreciar, tanto la vista diseño, donde gráficamente se ubican los
componentes y controles en el formulario, así como el código XAML (una variante del XML)
asociado a dichos elementos.
El Diseñador Grafico que se encargue de dicho formulario puede ubicar los controles
visualmente manipulando estos con el mouse, o puede directamente escribir en el código
XAML asociado, como si una página WEB se tratase.

Ing. Gabriel Esquivel 17


IFTS18 Introducción a C# 2018
Programming-Editing Time o Tiempo de Programación-Edición:
Se trata del momento en el cual el o los programadores empiezan a codificar y generar el
código fuente. Por lo general esto ocurre una vez que todos o al menos la gran mayoría de los
controles y componentes del Formulario ya han sido ubicados. Sin embargo, en algunos casos,
se puede hacer en paralelo con el diseño de los formularios, siempre y cuando exista una
buena coordinación por parte de los directores del proyecto.
A continuación se muestra un pequeño ejemplo de la vista de edición de código, donde
también se aprecia la ayuda que brinda el IntelliSense al momento de escribir una línea:
Figura 12. Vista Edición de Código de WPF

Código vinculado al
botón

IntelliSense

En el ejemplo mostrado, cuando el botón del formulario de WPF se presione, se ejecutará


inmediatamente el código que se está escribiendo con el intellisense.
Basándonos en el ejemplo previo de WPF, debajo se muestra como la capa de diseño de
formulario de ésta arquitectura se halla sobre la capa de código, permitiendo que, si el
proyecto está bien organizado, los artistas de diseño grafico implementen los formularios,
mientras, en paralelo, los programadores escriben su correspondiente código trabajando
todos en paralelo.

Ing. Gabriel Esquivel 18


IFTS18 Introducción a C# 2018

Figura 13. Capa de formulario y de código ejecutable de WPF

Control

Diseño de
Formularios

Vinculación
Lógica

Código Código Edición de


Vinculado al Vinculado al Código
Botón Botón Fuente

Compilación
Compilar el código es el acto que permite generar el código de máquina a partir del código
fuente.
Este acto lo realiza explícitamente el programador cuando acciona dicha opción de menú, o
implícitamente cuando depura y ejecuta el programa.
Antes, sobre todo en lenguajes intermedios como C y C++, el hecho de compilar un programa
era una etapa importante del desarrollo, ya que, tal como hoy en día, permite detectar errores
en el código fuente, generalmente errores de sintaxis. Afortunadamente, los entornos
modernos como el Visual Studio muchas veces compilan y chequean errores en tiempo de
edición, es decir, mientras el programador va escribiendo el mismo código. Esto es totalmente
cierto en Visual Basic .NET, se hace parcialmente en C#, y casi nada en Visual C++. Los errores
aparecen subrayados como si fuesen errores de ortografía, y también están enumerados en un
panel, el panel de Lista de Errores.
Debido a lo mencionado, la diferencia en productividad del VB .Net respecto a C# puede ser
apreciable, y mucho más aun respecto VC++, ya que no es necesario recompilar el proyecto
para ir detectando los posibles errores.
Debido a lo mencionado, dependiendo del lenguaje que se utilice, el hecho de compilar puede
pasar de ser algo muy importante a algo casi intrascendente.

Ing. Gabriel Esquivel 19


IFTS18 Introducción a C# 2018
Execution & Debugging Time o Tiempo de Ejecución y Depuración
Una vez que el programa o código ha sido escrito es necesario testearlo para poder garantizar
que responde a las especificaciones pedidas.
Entramos entonces en el tiempo de Ejecución, y casi con seguridad en la etapa de Depuración,
ya que muy raras veces no existen errores a corregir en un programa de envergadura.
Para poder depurar un determinado programa se cuenta con una gran variedad de poderosas
herramientas que permiten que el programador verifique el correcto funcionamiento de su
código.
Entre estas herramientas podemos mencionar:
 Breack Points o Puntos de Interrupción
 Step by Step Execution o Ejecución paso a paso
 Paneles accesorios como El Inmediato, el Automático…
Se verá más de estas herramientas en la sección Debug Programming o Execution Time
Programming.

Quality Test o Verificación de Calidad


Esto en realidad se realiza constantemente durante un desarrollo, pero es durante la
finalización del proyecto, cuando las versiones Alfa y Beta del producto están disponibles
cuando se torna realmente importante.
Es en esta situación cuando se hace vital que terceros, ajenos a la programación, denominados
habitualmente beta-tester, ensayen el producto de forma de relevar cuanta falla,
vulnerabilidad y error no esperado aparezca, e informen de estos a los desarrolladores para su
posterior corrección.

Ing. Gabriel Esquivel 20


IFTS18 Introducción a C# 2018

Clasificación de los Lenguajes


Si bien existen decenas de lenguajes de programación, aun sin incluir sus variantes, todos ellos
pueden ser incluidos en una de las siguientes categorías:
 Código de Maquina
 de Bajo Nivel
 de Nivel Intermedio
 de Alto Nivel
La diferencia entre cada uno de éstos radica en su complejidad de aprendizaje, y de
codificación, y en cuanto al destino tiene el código fuente una vez compilado (si se compila
como aplicación, una biblioteca, o como parte del firmware de un dispositivo electrónico).

Código de Maquina
Podemos definir al código de maquina como aquel código que directamente interpreta el
micro procesador-controlador.
Como es de esperar, a tan bajo nivel, el código aparece en binario puro, y por lo tanto es lo
menos amigable a la hora de programar.
Todos los lenguajes de más alto nivel tarde o temprano, antes de ser ejecutados son
traducidos a Código de Maquina, ya que como dijimos el Procesador trabaja exclusivamente
en este lenguaje. El proceso de convertir el código original a Lenguaje de maquina se
denomina habitualmente Compilación.
En el grafico que sigue, un bloque de código de maquina es engullido de alguna forma por el
micro procesador, y luego este se encarga de interpretar y procesar adecuadamente.
Figura 14. Ejecución de código de maquina

001010111001
101101110011
010111011101
011011011001
011010111001
001110111001
001110111001
010101110010
Código de Maquina Micro Procesador

Programación de Bajo Nivel


Bajo esta categoría tenemos lenguajes con algunas similitudes entre sí, pero muy
dependientes del dispositivo microcontrolador o microprocesador para el cual están
destinados.
Estos lenguajes en general son todos conocidos bajo el nombre de Assembler (o Lenguaje
Ensamblador para la jerga).
El paradigma de programación normalmente utilizado aquí es el de Programación
Estructurada, la cual se analizara más adelante.

Ing. Gabriel Esquivel 21


IFTS18 Introducción a C# 2018
Cabe destacar que la interacción del lenguaje con el Hardware es directa y total, es decir, no
existen limitaciones de ningún tipo para que, desde código, se lea o modifique el estado de un
determinado dispositivo hardware o posición de memoria (obviamente siempre hay
excepciones).
Como se imaginara, solo se lo utiliza en desarrollo de equipamiento electrónico que involucre
alguno de estos dispositivos, y quien lo utiliza generalmente es un programador especialista o
conocedor de la electrónica con dichos dispositivos.
Debajo en un grafico se ilustra cómo se genera el código de maquina a partir de la compilación
de un código en Assembler de un microcontrolador.
Figura 15. Compilación de código Assembler, y ejecución del código de maquina

Código Fuente en Assembler

do_msg: mov dptr, #mesg1


Compilación lcall pstr
lcall newline Instrucciones

mov dptr, #mesg2


lcall pstr
ret
mesg1: .db "This is a test messag", 'e'+128

001010111001 Ejecución
101101110011
010111011101
011011011001
011010111001

Código de Maquina Micro Procesador

Observe que, a pesar de que el código assembler probablemente no lo entienda (usted no


tiene porque saber assembler), este presenta una codificación estructurada, es decir, se puede
leer de izquierda a derecha y se ejecuta línea a línea, de arriba hacia abajo.

Programación de Nivel Intermedio


En esta categoría uno de los pocos representantes es el lenguaje C/C++. Este lenguaje se
caracteriza por su capacidad y poder para interactuar con el Hardware, pero manteniendo
algunas de las características de un lenguaje de alto nivel, haciendo que la hora de programar
sea más amena para cualquier programador.
Esto es tan así, que no hace mucho tiempo atrás se comenzó a utilizar cada vez más este
lenguaje como una alternativa más amigable que el Assembler. Lo que se hace muy a menudo
hoy en día es codificar con un IDE (aplicación utilizada para codificar) apropiado (como por
ejemplo el KEIL) el programa en C/C++, y esta aplicación se encarga luego de transformar el

Ing. Gabriel Esquivel 22


IFTS18 Introducción a C# 2018
código de nivel intermedio en uno compatible con el dispositivo electrónico, y como el mismo
procedimiento se realiza si se codifica en Assembler, los resultados finales son casi idénticos.
El mayor problema que puede acarrear el uso de C/C++ en lugar del Assembler, es que la
traducción del primero a código de maquina puede contener líneas innecesarias o
redundantes, ocupando de esta forma mayor cantidad de memoria, cosa que en un micro-
Controlador no siempre es admisible. También el incremento en las líneas de código de
maquina puede involucrar tiempos no optimizados de ejecución, haciendo a los algoritmos
más lentos que los obtenidos si se compilase assembler puro.
En el siguiente esquema volvemos a ver como las líneas del código fuente en C de un
microcontrolador son convertidas en código de maquina luego de la compilación.
Figura 16. Compilación de código fuente en C, y ejecución del código de maquina

Código Fuente en C

void main( ){
unsigned char j ; Instrucciones en
while( 1 ) { C/C++
Compilación
for (j = 0 ; j < 8 ; j ++ ) {
P1 = num[j] ;
delay_ms(500) ;
}
}

Micro Procesador
001010111001 Ejecución
101101110011
010111011101
011011011001
011010111001

Código de Maquina

También debemos mencionar que el C/C++ puede utilizarse en aplicaciones de alto nivel, como
por ejemplo formularios y bibliotecas, pero, dado que el lenguaje en si presenta ciertas
asperezas, este resulta menos competitivo para tales desarrollos, y es superado fácilmente en
productividad por los lenguajes de alto nivel.

Programación de Alto Nivel


En esta categoría se encuentran la gran mayoría de los lenguajes que actualmente existen.
Algunos ejemplos que podemos citar y que vamos a utilizar en ésta publicación son: Visual C++
y Borland C++, Visual Basic .Net, C# (o Visual C# .Net).
Hoy en día, casi la totalidad de estos lenguajes están orientados a sustentar el diseño de
Formularios tipo Ventana (a partir de ahora Formularios), Páginas Web y otros tipos de
proyectos, como las aplicaciones de Consola.

Ing. Gabriel Esquivel 23


IFTS18 Introducción a C# 2018
El paradigma aquí empleado en uso profesional, es el de la Programación Orientada a Objetos.
Con los lenguajes de esta categoría suelen ser fáciles o medianamente fáciles de aprender. Y la
creación de aplicaciones y proyectos también.
Una ilustración de lo que sucede se encuentra debajo:
Figura 17. Compilación de código fuente en C, y ejecución del código de maquina

Código Fuente en C#

public unsafe char[] ToCharArray()


{ Instrucciones
int length = this.Length; en C#
Compilación char[] array = new char[length];
Inicial if (length > 0)
{
fixed (char* ptr = &this.m_firstChar)
{
fixed (char* ptr2 = array)
{
string.wstrcpyPtrAligned(ptr2, ptr, length);
}

Código Intermedio
instance char[] ToCharArray () cil managed
{
Re IL_0000: ldarg.0
Compilación IL_0001: call instance int32 System.String::get_Length()
IL_0006: stloc.0
IL_0007: ldloc.0
IL_0008: newarr System.Char

Micro Procesador
001010111001 Ejecución
101101110011
010111011101
011011011001
011010111001

Código de Maquina

Ing. Gabriel Esquivel 24


IFTS18 Introducción a C# 2018

Paradigmas de Programación
Si bien existen varios paradigmas que permiten explicar metodologías o formas típicas de
programación, las siguientes 4 son básicos y permiten explicar fácilmente como hoy en día se
programa profesionalmente.
 Programación Estructurada
 Programación Orientada a Eventos
 Programación Orientada a Objetos
 Debug Programming ó Execution Time Programming

Programación Estructurada u Orientada a Métodos


Se caracteriza por presentar bloques de código perfectamente ordenados en secuencia. Esto
es, una serie de instrucciones exactamente definidas que se ejecutan una tras otra, hasta la
finalización del programa.
Un esquema simple de un bloque de este tipo sería el siguiente:
Figura 18. Esquema de ejecución de instrucciones en programación estructurada

Inicio Instrucción 1

ejecución
Instrucción 2

Instrucción 3 Fin

Un ejemplo básico en C# podría ser:


Figura 19. Esquema con instrucciones reales

Inicio int Min = 10


ejecución

int Max = 5, prom;

prom = (Min + Max) / 2; Fin

Una muestra real de código sería la siguiente:


Figura 20. ejemplo básico de código en C#

int Min = 10;


int Max = 5, prom;

prom = (Min + Max) / 2;

Console.WriteLine("el promedio es : {0}", prom.ToString());

En este caso, se han declarado 3 variables en las dos primeras líneas, y tras calcular el
promedio y almacenarlo en una de dichas variables, se procede a mostrar el resultado por la
salida estándar del sistema.

Ing. Gabriel Esquivel 25


IFTS18 Introducción a C# 2018
Funciones - Métodos
Una función (antes llamada subrutina, y en la actualidad método) no es más ni menos que un
bloque de código como el antes descrito, con la particularidad de que puede ser llamado a
voluntad desde cualquier otro bloque de código.
Por lo general una función permite resolver eficazmente una dada problemática, y es
reutilizada y llamada desde varias partes del código principal, tantas veces como sea necesario.
Un esquema muy básico es el siguiente:
Figura 21. Esquema de llamadas a función desde un bloque principal de código
función 1
Inicio Bloque principal
Instrucción
Instrucción 1

ejecución
Instrucción
Instrucción 2
Instrucción
Llamada a función 1
Ejecución

Instrucción 4 función 2
Instrucción
Llamada a función 2

ejecución
Instrucción
Instrucción 5
Instrucción
Fin

En el dibujo mostrado, el bloque principal de código llama a 2 funciones, las que retornan la
ejecución al bloque principal una vez que cada una de ellas concluye, y finalmente en la
instrucción 5 el bloque principal de código finaliza su ejecución.

Ing. Gabriel Esquivel 26


IFTS18 Introducción a C# 2018
Un ejemplo real con dicho esquema aparece a continuación:
Figura 22. Ejemplo real en C# de una aplicación de consola

static void Main(string[] args)


Delimitador de inicio de Función

Bloque principal de código


{
int Min = 10;
int Max = 5, prom;
Llamada a Función 1

prom =calcularpromedio(Min,Max);
Console.WriteLine("el promedio es : {0}", prom.ToString());

prom = CalcularMediaGeometrica(Min, Max);


Console.WriteLine("la media geometrica es : {0}",
prom.ToString());

Console.WriteLine("presione una tecla para salir");


ConsoleKeyInfo info = Console.ReadKey(false);
}
Delimitador de fin de Función
static int calcularpromedio(int a, int b)

Función 1
{
return (a + b) / 2;
}

static int CalcularMediaGeometrica(int a, int b)

Función 2
{
return a * b / 2; Función 2: recibe 2 parámetros
}

Como observará, las funciones a veces reciben parámetros, y otras veces devuelven un
resultado, como en estos dos ejemplos mostrados.
Para encerrar las instrucciones dentro de una función, siempre existe algún tipo de
delimitador, que en el caso de C# (al igual que en C/C++) son las llaves {}.
El resultado de ejecutar dicho código es la siguiente aplicación de consola:
Figura 23. Aplicación de consola, con los resultados de la ejecución

Ing. Gabriel Esquivel 27


IFTS18 Introducción a C# 2018
Este esquema de llamadas a función puede extenderse ilimitadamente, es decir, puede haber
funciones que llaman a funciones, que a su vez llaman a otras, así casi indefinidamente, como
se muestra debajo en un esquema.
Figura 24. Esquema de llamadas múltiples a funciones

Function 1 Function 3

Código
Principal

Function 4

Function 2
Function 5

Por desgracia, este paradigma tiene sus limitaciones. Una de las principales es el hecho de no
poder darle vida al código, ya que rápidamente se aprecia sus limitaciones, sobre todo si se
necesita una aplicación rica en controles, como los formularios de ventana. Sin embargo, este
paradigma sirve de sustento a los otros, que siendo más potentes, se basan en él.

Ing. Gabriel Esquivel 28


IFTS18 Introducción a C# 2018
Programación Orientada a Eventos
Evento
Un evento, tal como su nombre lo indica, no es más ni menos que un suceso que ocurre en
algún momento en alguno de los componentes del programa (código), o en el mismo sistema
operativo. Muchas veces, pero no todas, los eventos son lanzados o disparados por acciones
del usuario, como en el caso donde se presiona el botón de un formulario, o se presiona una
tecla, o se mueve el Mouse.
En este paradigma, se utilizan también bloques de código como funciones de la Programación
Estructurada, pero algunas de estas funciones son llamadas por lo que se denomina un Gestor
de Eventos (EventHandler), que no es más ni menos que un bloque de código ejecutable del
Sistema Operativo (o de alguna biblioteca muy vinculada a éste) que se encarga de manejar
estos sucesos.
Por lo tanto, bajo este paradigma, las funciones pueden ser llamadas tanto desde otra función,
como desde este manejador de eventos.
Un esquema básico de lo que sucede es el siguiente:
Figura 25. Lanzamiento y captura de evento

Manejador de Captura del


Eventos Evento

Function 2
Function 1
Lanzamiento
del Evento

Function 3 Function 4 Function 5

Como podrá apreciar, las funciones 1 y 2 solo se ejecutan si el manejador de eventos las llama,
y esto sucede solo si el evento ocurre, como por ejemplo, cuando el usuario hace clic en un
botón.
A veces se suele decir que la función captura el evento cuando el manejador de Eventos la
llama, ya que si se ignora la presencia de éste en memoria, es como si la función mágicamente
fuese ejecutada tras la aparición del Evento.

Ing. Gabriel Esquivel 29


IFTS18 Introducción a C# 2018
Un ejemplo de código que responde a tal esquema es el siguiente:
Figura 26. Ejemplo de código donde se captura un evento

public partial class Form1 : Form


{ Evento a capturar
public Form1()
{

Constructor
InitializeComponent();
this.button1.Click += new
System.EventHandler(this.button1_Click);
}

Función que captura


Manejador de Eventos Llamada a función
el evento

private void button1_Click(object sender, EventArgs e)

Función 1
{
MessageBox.Show("Hola señor!!");
}
}

En este ejemplo, existen 2 funciones declaradas, la primera de las cuales es un constructor de


una clase. Si se pregunta qué es un constructor, por ahora, solo le debería bastar saber que, un
constructor es un método más.
En dicho constructor, en la tercera y cuarta línea, con sintaxis de C# se le indica al sistema que,
debe asociar a la función button1_Click al evento button1.Click, esto manejado por
supuesto por su respectivo manejador de eventos (EventHandler).
Debido a ello, cada vez que el usuario haga clic con el mouse sobre el botón la función
button1_Click se ejecutará, tal como se había mencionado.
Tras ejecutar el código, y presionar el botón se observa lo siguiente:
Figura 27. Ejecución del código mostrado previamente

Si usted se toma el trabajo de borrar la línea donde se asocia al manejador de eventos, con el
evento y el método, observara que tras presionar el botón nada sucederá, tal demostrando la
funcionalidad del manejador de eventos.

Ing. Gabriel Esquivel 30


IFTS18 Introducción a C# 2018

Entorno de Desarrollo
El entorno es una aplicación sobrecargada de controles con distintos fines, que permiten en
forma visual o textual crear bibliotecas de clases y controles, y aplicaciones.

Editor de Código
Debajo podemos apreciarla:
Figura 28. Vista del Editor de Código y sus Tabs (Pestañas)
Panel de Barra de Panel Explorador
Barra de Menús de Soluciones
controles Herramientas

Panel de Editor de Código


Resultados

En éste podemos resaltar:


 Barra de Menús.
Como en cualquier aplicación, contiene Menús desplegables con una gran variedad de
herramientas y opciones para interactuar con el proyecto.
 Barra de herramientas
Similar al anterior, pero solo consta de botones con íconos indicativos de función que
realizan.
 Paneles desplegables
Los más destacados son:
o Explorador de soluciones

Ing. Gabriel Esquivel 31


IFTS18 Introducción a C# 2018
o Panel de Propiedades
o Cuadro de Herramientas
o Cuadro de Ayuda
o De Resultados e Inmediato
o Lista de Tareas
o Automático
o Variables Locales
 Pestañas (Tabs)
En las Pestañas aparece la información de diseño del Proyecto. Ésta puede aparecer en
diferentes formatos:
o Diseñador de Formularios y Controles: Permite crear y modificar en forma visual un
formulario de aplicación o un control de usuario. A éstos es posible agregarles
manualmente otros controles eligiendo cuales en el cuadro de herramientas y
dibujando sobre el formulario o control de usuario.
o Editor de Código: El código que determina la apariencia del formulario o control de
usuario y el comportamiento de éste aparece en otra página, accesible mediante una
pestaña.

Diseñador/Editor de Formularios
Otra imagen del Entorno de desarrollo aparece a continuación:
Figura 29. Vista del diseñador de formularios

Formulario o control en Tab del Diseñador Panel Explorador


Vista Diseño de Formularios de Soluciones

Cuadro de Herramientas con Panel del Editor de Código Panel de


controles para formularios XML del Formulario Propiedades

Ing. Gabriel Esquivel 32


IFTS18 Introducción a C# 2018

Proyectos y Soluciones
Cada vez que nos proponemos hacer una aplicación o una biblioteca vamos a generar una
Solución y al menos un Proyecto que formará parte de dicha Solución.
Sin embargo, si deseamos por ejemplo que las clases de bajo nivel se encuentren disponibles
para ser utilizadas por otras aplicaciones, seguramente generaremos una Biblioteca .dll que
contenga a dichas clases, por lo tanto en nuestra solución tendremos que generar otro
Proyecto, en éste caso el de una Biblioteca de Clases.

Panel Explorador de Soluciones


En el Explorador de Soluciones podremos ver a todos los Proyectos que forman parte de
nuestra solución, y en éstos a cada uno de los archivos que conforman cada proyecto. Por
ejemplo:
Figura 30. Vista del explorador de soluciones y su contenido

Solución

Proyecto 1

Proyecto principal

Referencias a
Bibliotecas

Archivo de
Formulario XAML

Las Referencias a Bibliotecas permiten acceder a clases fuera de nuestro proyecto, por
ejemplo a la clase UserControl que permite generar un nuevo formulario WPF y se halla en el
namespace System.Windows.Controls dentro de la biblioteca PresentationFramework.dll. Son
una “especie de acceso directo” para acceder al contenido de la .dll especificada.

Ing. Gabriel Esquivel 33


IFTS18 Introducción a C# 2018
Los formularios tienen la extensión .xaml.
Para aclarar mejor el tema veamos una descripción de algunos de los archivos más utilizados:
De uso habitual
Tipo de Archivo icono Descripción
Almacena información sobre uno o varios proyectos, los cuales
Solución pueden ser de C#, Visual Basic .NET, Visual C++ .NET o una
combinación de ellos.
Contiene información a cerca de un grupo de archivos de código de
Proyecto de Visual C#
C# y quizás la de otros tipos de archivos (por ejemplo imágenes).
Contiene código donde se definen clases, interfaces o estructuras la
Código en C#
extensión del archivo es .cs
Formulario XAML de Archivo de código XAML que define un Formulario o control de
WPF usuario WPF. La extensión es .xaml
Referencia a una
biblioteca
Propiedades

Panel de Propiedades
El Panel de Propiedades utiliza un ComboBox en modo diseño para seleccionar el objeto que se
desea inspeccionar y/o modificar, y un PropertyGrid que muestra todas las propiedades
visibles1 del objeto seleccionado. Por ejemplo, para el formulario de la Figura 29. tenemos:
Figura 31. Vista del panel de propiedades

ComboBox para
la selección de
Opciones del Formulario o
PropertyGrid Control. Permite
seleccionar otros
objetos

Grupo de
Propiedades
contraído

Propiedades
agrupadas por
categoría

Propiedad
seleccionada

Valor de la
Propiedad

1
Es posible declarar propiedades que no son visibles al Panel de Propiedades

Ing. Gabriel Esquivel 34


IFTS18 Introducción a C# 2018
Examinador de Objetos
El Tab del Examinador de Objetos permite observar muchas de las características de los
objetos contenidos por las Bibliotecas cargadas, como ser:
 Bibliotecas (Ensamblados) que se hallan cargadas o son utilizadas en el Proyecto.
 Ruta de dichos archivos de Bibliotecas.
 Nombres de Espacio que contienen.
 Enumeraciones, Clases, Interfaces, Delegados y Estructuras que contiene cada Nombre de
Espacio y cada Biblioteca.
 Miembros de cada Clase, Interfaz, Delegados y Estructura, la descripción, la declaración y
el Tipo de cada Miembro.
 Jerarquía de herencia de una clase
Figura 32. Vista del Examinador de Objetos
Clase Button seleccionada y Miembros de la clase
su jerarquía de herencia seleccionada

Miembro seleccionado
(la clase en éste caso)

En la declaración de los miembros se podrá ver el Tipo de objeto específico del Miembro, así
como los Parámetros que se le pasan. En el ejemplo de la figura anterior el objeto
seleccionado es Button, y se puede apreciar que es una clase que hereda de ButtonBase, y se
encuentra en System.Windows.Controls.

Ing. Gabriel Esquivel 35


IFTS18 Introducción a C# 2018
Entre los iconos que podemos encontrar tenemos:
Tipo icono
Éstos serán descriptos en forma más
Nombre de Espacio
detallada en las páginas siguientes.
Objetos
Clase
Estructura
Interfaz
Enumeración
Delegado
Miembros
Variable Miembro
Método
Propiedad
Evento
Constantes

Ing. Gabriel Esquivel 36


IFTS18 Introducción a C# 2018

Aplicaciones y Formularios
Veamos un ejemplo simple de cómo generar una aplicación básica.

Creación de un nuevo Proyecto


Para ello procedemos a presionar el botón Nuevo Proyecto en la barra de herramientas
principal. Tras esto aparecerá el siguiente cuadro de diálogo:
Figura 33. Asistente para la creación de proyectos

Como podrá apreciar, las opciones son varias, desde la elección del lenguaje de programación
hasta la posibilidad de indicar el tipo de proyecto de salida.
Para nuestro ejemplo las opciones son las indicadas en la imagen previa. Tras presionar el
botón Aceptar obtenemos una imagen como el de la Figura 29.
Los archivos generados tras éste primer paso son los siguientes:
Figura 34. Contenido del directorio donde se aloja nuestro proyecto

Ing. Gabriel Esquivel 37


IFTS18 Introducción a C# 2018
Como podrá observar, aparecen los archivos mostrados por el explorador de soluciones, entre
otros. Entre los directorios podemos distinguir:
 bin: almacena por defecto (se puede especificar otro directorio) los archivos compilados
(ejecutables y/o bibliotecas) y todos los archivos de biblioteca incluidos en las referencias
(salvo aquellos archivos del sistema y los que explícitamente se indica que no se realicen
copias al directorio).
 obj: en éste directorio se almacenan muchos de los archivo temporales que se generan
durante la compilación. Por lo general, no reviste mayor importancia el contenido de éste
directorio para un programador.
A ésta altura ya es posible correr la aplicación, solo que aparecerá un formulario vacío como el
mostrado en el mismo Diseñador de la Figura 29. Para ello, solo debe presionar el botón Iniciar
(Run en ingles) o presionar F5 si tiene el teclado configurado como Usuario de Visual Basic.
El código generado por el diseñador aparece a continuación:
Figura 35. Vista del código autogenerado por el diseñador de formularios

Ing. Gabriel Esquivel 38


IFTS18 Introducción a C# 2018

Figura 36. Vista del Formulario WPF en modo diseño

Ing. Gabriel Esquivel 39


IFTS18 Introducción a C# 2018

Programación Orientada Objetos


Concepto de Objeto
Los objetos en programación tienen muchas similitudes con un objeto de la vida cotidiana,
obviamente de allí deriva su nombre.
Uno puede llegar a verlos como un algo con:
 características como el color, la masa, la posición… en POO mediante propiedades se
puede disponer de estas características
 comportamientos ante excitaciones externas o internas… utilizando captura de
eventos
 a veces se le puede pedir cosas, a través de los Métodos
Por ejemplo, piense en una aplicación de ventana de uso corriente: ésta poseerá Propiedades,
como el color de fondo del formulario, un título, un icono de aplicación, un cursor para el
ratón, etc.
También generará eventos ante diferentes estímulos, por ejemplo al redimensionar el
formulario, al cambiar el color de fondo, etc., y se le puede pedir que haga varias cosas
mediante sus métodos, por ejemplo para cerrar un formulario se puede llamar al método
Close, a Activate para que obtenga el foco, etc.
Una ilustración de un posible objeto genérico se muestra debajo:
Figura 37. Estructura celular de un objeto: encapsulamiento

Encapsulado método
público

método 1 método 2

método
privado

método 3 método 4 método 5

Variable
Local
propiedad

Variable Variable Variable


Global 1 Global 2 Privada

Ing. Gabriel Esquivel 40


IFTS18 Introducción a C# 2018
Como observará, las variables globales son privadas 2 (o protegidas) para evitar que cualquiera
desde fuera manipule un objeto. En cuanto a los métodos, pueden ser public o private
(también internal y protected son admitidos).
El acceso a las características del objeto se hace mediante propiedades, que generalmente son
públicas.

Miembros de un objeto
A éstas características que poseen los objetos se las denominan miembros y entre ellas
podemos mencionar:
 Variables Miembro – en POO se las denomina campos
 Las Propiedades
 Los Métodos – antes se llamaban funciones
 Los Eventos
La declaración de un objeto mediante código se hace con la palabra reservada class (clase), y
será analizada a continuación.

Clases
Una clase es el código de declaración de un objeto, mientras que un objeto es una instancia de
una clase.
Es como hablar de los planos de un barco (la clase) y del propio barco (el objeto o instancia de
la clase). Crear más instancias de una clase es como construir otros barcos idénticos, solo que
cada barco luego podrá tener sus propias características distintivas, como el color de la
cubierta, nombre, tripulación, etc.
Heredar de una clase es como diseñar un nuevo barco utilizando como base los planos del
primero. Debido a ello habrá seguramente muchas similitudes entre ambos.
Las clases se pueden declarar de la forma que aparece debajo:
Formas de Declaración Descripción
public class sprite
{
Ésta es la forma usual de declarar una clase básica. Los
protected Color color; miembros de la clase se pueden escribir en cualquier
protected float rotation; orden dentro de la sentencia mostrada, como por
⋮ ejemplo el color y la rotación del sprite.
}

Herencia
Una de las herramientas más potentes de .Net y la POO es el uso de la herencia. Mediante ésta
es posible generar objetos que posean todos o casi todos los miembros de otros (elegidos a
voluntad por el diseñador) que sirven de base para la herencia.
Obviamente también es posible ahorrar y optimizar mucho el código mediante éste
mecanismo, ya que clases que mantengan cierta similitud pueden heredar de una única clase
base que implemente el código común.

2
El uso de public o internal en una clase, no está prohibido en absoluto, pero sin embargo está mal visto,
ya que pone en peligro la integridad de los datos del objeto.

Ing. Gabriel Esquivel 41


IFTS18 Introducción a C# 2018
Por ejemplo, debajo se muestra el diagrama de clases que ilustra como todos los objetos
dibujables en nuestro juego heredan de sprite.
Figura 38. Árbol de herencia

También se puede apreciar que DestruibleSprite hereda de sprite, y tanto Alien, boss y Player
heredan indirectamente de éste último, ya que todos son plausibles de ser destruidos. En otras
palabras, la lógica de los dibujos se encuentra en sprite, y la de la destrucción de un dibujo en
DestruibleSprite.
Un ejemplo simple de código se muestra debajo:
Formas de Declaración Descripción
public class Cuando se utiliza la herencia se apela a la forma
DestruibleSprite:sprite
mostrada. Los : indican que la clase
{
⋮ DestruibleSprite hereda de la clase escrita a la
} derecha, en éste caso de sprite

Interfaces
Dado que la herencia multiple no existe en .Net y C#, una alternativa menos poderosa es
utilizar la implementación de interfaces, como a continuación se muestra:
Declaración Descripción
public interface IDestruible La declaración es similar a la declaración de una clase,
{ solo que no está permitido indicar el nivel de
int Health { get; set; }
} accesibilidad de sus miembros…
En esencia, la Interfaz permite indicar de antemano al menos que miembros estarán
disponibles en las clases que implementen dicha interfaz. Por ejemplo, debajo la clase
DestruibleSprite posee también3 el campo Health:

3
De hecho, la clase está obligada a contener dicho miembro, por eso se suele hablar de que una interfaz
es como un contrato, en el sentido de que obliga a la clase a poseer sus miembros…

Ing. Gabriel Esquivel 42


IFTS18 Introducción a C# 2018
Uso Descripción

public class DestruibleSprite:sprite, IDestruible La forma mostrada indica que


{ la clase DestruibleSprite hereda
public int Health { get; set; }

de la clase sprite e implementa
} la Interface IDestruible.

Si la clase implementa más de una Interface entonces se deberá separar por comas tantas
veces como Interfaces implemente.

El Constructor
Se trata de un método que se debe correr antes de utilizar al objeto, ya que éste permite que
se cree e inicialice dicho objeto.
La idea es que en éste método se inicializan cada una de las variables miembro. Por ejemplo:
Formas de Declaración Descripción
public class sprite
{ En éste caso el objeto sprite posee
protected Vector2 scale, origin, velocity; varias variables globales, las que se
protected Color color; inicializan dentro del constructor.
public sprite() Todas son importantes, como scale
{ para el factor de escala utilizado al
scale = new Vector2(1.0f); dibujar el sprite, o color, que
origin = new Vector2();
color = Color.White; permite cambiar el color de todo el
} objeto al dibujarlo, etc.
}

Constructores con parámetros


Por supuesto, puede haber constructores que utilizan parámetros, lo cual es muy útil para
inicializar con diferentes valores a un objeto. Un ejemplo se halla a continuación:
Declaración
public class bullet:sprite
{
sprite Owner;

public bullet(sprite owner, Vector2 velocity)


{
Owner = owner;
Posicion = owner.Posicion;
this.velocity = velocity;
}
}
Descripción
Aquí la clase bullet (los proyectiles utilizados tanto por jugadores como por los aliens) contiene
una variable miembro Owner que indica quien lanza el proyectil. Para inicializarla
adecuadamente, se le pasa el valor externamente con el parámetro owner.
A su vez, se utiliza ésta para obtener la posición inicial de la bala en la segunda línea, ya que el
proyectil saldrá inicialmente de la ubicación de quien lo lanza.
Otro parámetro utilizado es velocity, el cual inicializa la velocidad del proyectil de una forma
similar.

Ing. Gabriel Esquivel 43


IFTS18 Introducción a C# 2018
Para invocarlo se utilizan líneas como ésta:
Declaración
protected virtual void Shot(int shotrate = 30)
{
if (rnd.Next(shotrate) == 1)
{
game.NewSprites.Add(new bullet(this, new Vector2(0, 6)));
}
}
Descripción
El método Shot es utilizado en los aliens para disparar.
En la primera línea con el if se chequea la probabilidad de disparar mediante el parámetro
shotrate (cuanto mayor sea este número, menor es la probabilidad de disparo).
En la segunda se declara y al mismo tiempo se instancia un objeto de la clase sprite con la
palabra reservada new, llamando de ésta forma al constructor antes analizado. Con el this se
le indica al proyectil que éste alien es quien hace el disparo.

Constructor en Clases Heredadas


En las clases hijas es usual que se deba llamar al constructor de la clase padre, por si éste hace
alguna inicialización importante. Para ello se utiliza la palabra reservada base como se muestra
a continuación:
Declaración
public class bullet:sprite
{
sprite Owner;
public int Energy { get; protected set; }

public bullet(sprite owner, Vector2? velocity = null, int energy = 2): base()
{
Posicion = owner.Posicion;
if (velocity != null)
this.velocity = (Vector2)velocity;
else
this.velocity = new Vector2(0, -10);
scale = new Vector2(2.0f);
Owner = owner;
Energy = energy;
}
}
Descripción
Aquí ampliamos el ejemplo previo.
La primera línea del constructor debe incluirse la llamada al constructor de la clase base, con
los :base(), debido a que el propio sistema nos obliga a llamarlo así.
El segundo parámetro del tipo Vector2? indica que el parámetro puede ser del tipo Vector2 o
un null. Ésta importante novedad, los tipos nulleables fue agregada hace unos años, haciendo
posible hacer null las variables por valor.

Ing. Gabriel Esquivel 44


IFTS18 Introducción a C# 2018
Clase no heredable – sealed
A veces el desarrollador desea que algunas de sus definiciones de clases no puedan ser
heredadas, generalmente por un tema de seguridad (en su más amplio sentido), entonces
puede recurrir al uso de la palabra reservada sealed.
Ejemplo
public sealed class DrawingUtilities
{

}

Ejemplos de clases de éste tipo son:


 la utilizada para graficar en pantalla, denominada Graphics.
 La clase Font que contiene información sobre fuentes.
Debajo podemos ver las definiciones y comentarios de éstas clases mostradas por el
explorador de objetos del Visual Studio
Figura 39. Vista simple de la clase sellada Graphics

Figura 40. Vista simple de la clase sellada Font

Lo mencionado en éste caso tiene su razón: cualquier modificación mediante herencia hecha
por terceros en estas clases haría que prácticamente fuera imposible compatibilizar los cientos
o miles de soluciones posibles, es decir, cada uno haría lo que querría y eso conduciría al caos.

Ing. Gabriel Esquivel 45


IFTS18 Introducción a C# 2018
Clases no instanciables – abstract
Algunas veces podemos crear clases que no implementan el código de algunos de sus métodos
o propiedades (ya se han analizado los miembros abstractos y los virtuales), o simplemente la
clase solo sirve de referencia para las futuras clases hijas. Ante dicha situación se utiliza la
palabra reservada abstract, quedando un código como el siguiente:
Declaración
public abstract class sprite
{
public abstract void Update(GameTime gameTime);

public abstract void Draw(GameTime gameTime);

public abstract void LoadContent();

protected virtual void CheckHorizontalPosition()


{
if (Posicion.X > game.Graphics.GraphicsDevice.Viewport.Width - 10 ||
Posicion.X < 0)
velocity = new Vector2(-velocity.X, velocity.Y);
}
}
Descripción
La clase sprite sirve de base para todos los objetos 2D que serán dibujados en el juego. Para
ello, posee 3 métodos abstractos, y otros virtuales (solo se muestra 1...).
Debido a que no posee código en algunos de sus métodos estamos obligados a declararla
como abstract. Sin embargo, si tuviese todos sus métodos con código propio, como solo es
una base para futuras clases igualmente la declararíamos abstracta.

Clase estática – static


En muy raras ocasiones una clase posee solo constantes y métodos (static) compartidos. Ante
tal situación se hace uso de la palabra reservada static.
Ejemplo
public static class DrawingUtilities
{

}

Dicha clase no podrá ser instanciada, ni se podrá obviamente tener variables de dicho tipo.

Ing. Gabriel Esquivel 46


IFTS18 Introducción a C# 2018
Un ejemplo claro y representativo de dichas clases es la clase Math, la cual se muestra debajo
junto a algunos de sus miembros:
Figura 41. Vista de la clase estática Math y sus miembros

Reemplazo de Miembros en Clases Heredadas


La herencia es una herramienta muy eficaz y poderosa para la reutilización del código, pero
siempre existe la posibilidad de que un nuevo tipo de objeto que utiliza la herencia no se
corresponda con el código de la clase base de la cual hereda. En estas circunstancias es posible
utilizar el reemplazo de los miembros de la clase base:

abstract, virtual y override


Las palabras reservadas que se utilizan son:
 virtual: Indica que el miembro puede ser reemplazado por una clase que hereda de la
clase padre.
 override: Utilizada en la clase hija para indicar que el miembro reemplaza a uno de la
clase base.
 abstract: En una clase no implementable (del tipo abstract) algunos de sus miembros
pueden no contener código, pero deben llevar ésta palabra delante indicando que las
clases herederas deben implementar el código de dicho miembro o ser también
abstractas.
Debajo unos ejemplos explican mejor lo antedicho.

Ing. Gabriel Esquivel 47


IFTS18 Introducción a C# 2018
abstract
Cuando se planifica con antelación un proyecto, algunos objetos padres contendrán código
básico en sus propiedades y métodos, y se declararán otras propiedades y métodos sin código,
que deben ser reemplazados casi con obligación en las clases hijas. Estos métodos y
propiedades sin código deben contener la palabra reservada abstract, haciendo que la clase se
vuelva también abstracta:
Formas de Declaración
public abstract class sprite
{
public abstract void Update(GameTime gameTime);

public abstract void Draw(GameTime gameTime);

public abstract void LoadContent();


}
Descripción
En éste ejemplo se declara la clase base de todos los dibujos 2D que serán nuestros
personajes, naves, y objetos de nuestro juego. Un ejemplo claro son los aliens, cuya clase
hereda de sprite.
Está clase base contiene los 3 métodos abstractos mostrados:
 LoadContent: permite cargar por ejemplo los gráficos 2D y los sonidos entre otros
recursos
 Update: utilizado para actualizar datos e información dentro del objeto
 Draw: todos los dibujos en algún momento deben dibujarse, para eso está este
metodo

Solo debe tener en cuenta que la accesibilidad del miembro reemplazado debe respetarse en
las clases hijas.

virtual
En la POO es usual que se creen objetos padres que contengan métodos declarados con un
algoritmo que resuelve una situación básica, pero con antelación se prevé que se necesitará en
algunas de las clases hijas una solución o algoritmo diferente. Para éstas situaciones se pueden
declarar métodos o propiedades virtuales como el siguiente:
Formas de Declaración Descripción
public virtual int Health {
get Aquí la propiedad Health de los objetos plausibles de ser
{ destruidos, como los aliens y el jugador, se declara como
return health;
virtual, ya que es posible que alguna clase a futuro
}
set requiera un comportamiento distinto al implementado en
{ ésta clase.
if (Shield <= 0) En particular, aquí en el sub método set se implementa la
health -= value;
else lógica del escudo de energía shield, el cual, siempre que
Shield -= value; esté activo impedirá que la energía health del objeto bajo,
} a expensas de parte del escudo de energía.
}

Ing. Gabriel Esquivel 48


IFTS18 Introducción a C# 2018
Reemplazo de Métodos - override
los métodos o propiedades declarados como virtuales o abstractos pueden reemplazarse en
las clases hijas utilizando la palabra reservada override, como se muestra a continuación:
Formas de Declaración Descripción
public abstract class DestruibleSprite:sprite Como se puede apreciar, la clase
{ DestruibleSprite hereda de sprite
public enum State
{ (los dos puntos indican ello).
live, dying, died Luego, se declara una
} enumeración y una variable que
protected State state;
indican el estado del objeto: vivo,
muriendo, y muerto.
public override void Draw(GameTime gameTime) El método que reemplazamos es
{
Draw. Su código permite dibujar
if (state == State.live)
{ en el caso de que esté vivo el
DrawShield(); escudo de energía y la salud del
DrawHealth(); objeto, ya que es la única
}
} información que hasta ahora
} tenemos.

Otra muestra más podría ser ésta:


Formas de Declaración
public class Player : MultiFrameSprite
{
public override void Draw(GameTime gameTime)
{
game.spritebatch.DrawString(font, Score.ToString(), StatsPosition,
Color.Snow);

game.spritebatch.Draw(textura, Posicion, rectangles[currentframe],


color, rotation, origin, scale,
spriteeffects, 1.0f);
base.Draw(gameTime);
}
}
Descripción
Volvemos a reemplazar al método Draw, en éste caso en la clase Player. Aquí primero se
dibujan las estadísticas del jugador con el método game.spritebatch.DrawString(...), luego se
dibuja a la nave del jugador, y finalmente se deja que las clases padres hagan lo que saben
(dibujar el escudo de energía, la salud, etc.)

Ing. Gabriel Esquivel 49


IFTS18 Introducción a C# 2018
Sombreado - new
Mediante el uso de la palabra reservada new es posible pisar completamente y cambiar todas
las características de un miembro. A dicho procedimiento se lo denomina Sombreado.
Siguiendo con los ejemplos anteriores, fíjese en esto:
Formas de Declaración Descripción
Como podrá apreciar, todas las características del método
private new int Update() original fueron cambiadas:
{
 El nivel de accesibilidad cambiado a private
}  Ahora Update devuelve un valor entero
 la cantidad de parámetros es nula
Sin embargo existen situaciones donde el miembro que reemplaza no es 100% accesible por su
nivel de accesibilidad y entonces el sistema devuelve una referencia al miembro sombreado,
por lo tanto ambos coexisten en el objeto, pero solo uno será accesible. Esto hace que en
algunas situaciones se produzcan efectos indeseados con el miembro en cuestión.

Casteo
Gracias a la herencia es posible manipular objetos que han heredado de una cierta clase con
una referencia del tipo de su clase padre. Esto es muy útil debido a que a veces no es
necesario saber exactamente de qué subclase es un dado objeto, solo basta con transportarlo
y manipularlo usando los miembros disponibles en su clase base.
Por ejemplo, dado que object es la clase base de todos los objetos de .Net, es posible pasar
una referencia de cualquier cosa en un método que utiliza un parámetro de éste tipo. No es
casualidad que en los métodos asociados a eventos uno de los parámetros sea de éste Tipo,
como se puede ver debajo:
Forma de Declaración

Protected Sub vScrollBar1_Scroll(ByVal sender As Object, _


ByVal e As ScrollEventArgs) _
Handles VScrollBar1.Scroll

End Sub

Descripción
El evento de Scroll de un VerticalScrollBar es capturado por el método mostrado. El primer
parámetro denominado sender es del tipo Object, y está pensado para transportar una
referencia del Objeto que genera el Evento, el cual puede ser de cualquier Tipo.

A veces se desea acceder a los miembros del objeto heredado no disponibles en el Tipo del
objeto utilizado, como se ve debajo.
Forma de Declaración

Ing. Gabriel Esquivel 50


IFTS18 Introducción a C# 2018
En ese caso recurriremos al Casteo (Cast) utilizando la palabra reservada CType:
Forma de Declaración

Descripción
Observe que ahora luego del Casteo todos los miembros del objeto control están disponibles,
aunque sender no sea un control.
Obviamente, antes de Castear al objeto debemos asegurarnos de que sea del Tipo al cual
pretendemos Castear, ya que si no saltará una Excepción.

Para ello recurrimos a una clausula donde preguntamos si el Tipo del objeto sender es …
(Control en el ejemplo)

Palabras Reservadas “this”, “base”


Si queremos acceder a un Figura 42. Uso típico del this y vista de sus miembros
miembro de la clase donde
actualmente nos encontramos
podemos utilizar la palabra
reservada this como se aprecia
a la derecha.
Resulta muy útil, ya que es
usual que en las clases
importantes con gran cantidad
de código el número de
miembros puede ser muy Figura 43. Uso típico de la palabra reservada base
elevado y no siempre el
programador recuerda con
exactitud cada uno de ellos.
En tanto que, para el acceso a
miembros heredados
utilizaremos la palabra base
como en el ejemplo
siguiente:
Tenga en cuenta que solo
serán accesibles los miembros public, internal y protected de la clase base, ya que los private
solo son accesibles dentro de la Clase donde fueron declarados.

Ing. Gabriel Esquivel 51


IFTS18 Introducción a C# 2018
Variables Miembro o Campos
Son las clásicas variables globales de la programación tradicional.
Lo más usual es que un objeto contenga una o varias de éstas variables miembro, y
generalmente en la programación orientada a objetos son tipo private o protected, es decir,
no serán accesibles por objetos externos. Ello se debe a que usualmente el acceso a la
información interna del objeto es a través de otro miembro denominado Propiedad, la que es
descrita más adelante.
Formas de Declaración Descripción
Se puede declarar tal como aparece a la izquierda: Primero el
Tipo de Dato, y luego el nombre de la variable . En éste caso
Color color; tomará la accesibilidad por defecto private.
Observe además que, el nombre de la variable color en éste caso
coincide con el Tipo de Dato Color
Otra forma es la mostrada, primero la palabra indicando el nivel
protected Color color; de acceso, luego el Tipo de dato almacenado y finalmente el
nombre de la variable.
El término protected se describe junto a otros a continuación:

Niveles de Acceso
Permiten que los miembros u objetos sean accesibles o no externamente a los objetos o
Ensamblados (Bibliotecas o Ejecutables) que los contienen.
Las opciones posibles ordenadas por nivel de accesibilidad decreciente son:
Nivel de Acceso Accesibilidad
public Es accesible dentro y fuera de la Clase o Biblioteca según corresponda.
Internal Es accesible solo por objetos dentro del Ensamblado
No es accesible fuera de la clase, pero si es heredable y accesible
protected
internamente por una clase heredada o hija
No es accesible fuera de la clase (en el caso de los miembros) o de la
private
Biblioteca (para una Clase o Estructura).

Métodos
Las antiguas funciones y subrutinas se agrupan ahora bajo el nombre de Método. Se trata de
un conjunto de líneas de código que pueden ser llamados a voluntad las veces que queramos y
pueden o no devolver objetos o valores.
Las más simples se declaran así:
Formas de Declaración Descripción
protected void DrawShield()
{ La palabra reservada void indica que el método no devuelve
⋮ nada luego de ejecutarse.
}
La palabra reservada int indica que el método devuelve un
protected int DrawHealth() valor entero luego de ejecutarse. Éste valor entero
{
probablemente brinda alguna información relevante a quien

} llamo el método.
El Tipo devuelto puede elegirlo el programador a voluntad.

Ing. Gabriel Esquivel 52


IFTS18 Introducción a C# 2018
Formas de uso Descripción
⋮ Para llamar al método, simplemente hacemos uso de su
DrawShield(); nombre, luego los típicos paréntesis, y el fin de línea clásico
⋮ de C, el punto y coma.

int a; En el caso de que el método devuelva 1 valor, usualmente
a = DrawHealth(); una variable recibe éste como en el ejemplo mostrado.

Parámetros
Muchas veces es necesario pasar algún tipo de información a un método, y para ello existen
los denominados parámetros o argumentos. La cantidad y tipos de éstos no está restringida4.
Declaración Descripción
public void Shot(int shotrate) En este caso se pasa un parámetro tipo entero. El
{
parámetro solo puede utilizarse dentro del método, es

} decir, ese es su ámbito.
Internamente un parámetro se comporta como una variable mas, solo que el valor es seteado
fuera del método.
Los métodos reciben parámetros, y éstos pueden pasar bajo 2 formas bien distintas:
 por valor
 por referencia

Parámetros pasados por Valor


Cuando la variable parámetro es del Tipo por Valor las posibilidades son:
Variable del Tipo Valor Descripción
La variable entera por valor por defecto es pasada por
Valor, y será una copia de la variable original que se pasó
public void Shot(int shotrate) al llamar al método, por lo tanto shotrate es una variable
{

local.
} Todo cambio a dicha variable dentro del método no
afectará a la variable original, sino que solo a la copia
local.

Variable del Tipo Referencia Descripción


El parámetro gameTime es una copia de la
Variable de Referencia utilizada al llamar al
public void Update(GameTime gameTime) método, por lo tanto también es una referencia
{
⋮ al objeto referenciado por la variable original.
} Cualquier cambio realizado en la variable
gameTime local, afectara también a la variable
original fuera del método.

4
El número de parámetros máximo puede ser tan grande que usualmente no es algo que preocupe a los
programadores.

Ing. Gabriel Esquivel 53


IFTS18 Introducción a C# 2018
Parámetros pasados por Referencia
En ocasiones es deseable que las variables por valor sean modificadas dentro del método, y
regresadas así fuera de éste.
Para tales situaciones, se utilizan las palabras reservadas ref o como alternativa out.
Variable del Tipo Valor Descripción
Aquí la variable shotrate es una referencia a la
variable original del tipo Integer, produciéndose lo
public void Shot(ref int shotrate) que se denomina Encapsulamiento.
{ Operar con la variable del Tipo por Valor pasada
⋮ por referencia es como operar directamente con la
shotrate = 10; variable externa al método, y por lo tanto,

cualquier modificación en la variable local afectará
}
al valor de la variable externa. En éste caso,
shotrate devolverá el valor 10 al salir de la
función.
La otra opción posible es:
Variable del Tipo Valor Descripción
La otra opción viable es utilizar la palabra
public void Shot(out int shotrate) reservada out. La diferencia con ref es que en la
{

primera, la variable debe ser inicializada antes de
} llamar al método, pero con out no es necesaria
dicha inicialización.

Forma de uso Descripción


⋮ Cuando se hace el llamado a la función, debe incluirse
int rate = 30;
Shot(ref rate);
junto al parámetro la correspondiente palabra ref u
⋮ out según corresponda.

Finalmente, la opción restante sería una variable por referencia pasada por referencia! Todo
indica que no existe una situación real donde ésta opción sea útil.

Sobrecarga
Una de las novedades frente a la programación tradicional es la posibilidad de crear varios
métodos u operadores con el mismo nombre, con la condición de que éstos tengan diferentes
tipos de parámetros o diferente cantidad de éstos.

Ing. Gabriel Esquivel 54


IFTS18 Introducción a C# 2018
Sobrecarga de Métodos tradicional
Imagínese por ejemplo que la cantidad de disparos, la energía de cada uno y el tipo de disparo
que efectúan los aliens se pudiese controlar con diferentes métodos, cada uno con una
cantidad diferente de parámetros, pero todos unidos o vinculados por un método llamado
Shot, bajo dicha situación, el código quedaría algo así:
Formas de Declaración
protected void Shot(int shotrate)
{

}

protected void Shot(int shotrate, int energy)


{

}

protected void Shot(int shotrate, int energy, int multiburts)


{

}
Descripción
En éste caso los tres métodos se diferencian en la cantidad de parámetros, pero podría ser
también en el tipo de alguno de ellos.
Al utilizar el método podemos ver en el intellisense:
Forma de uso Descripción

Observe como aparecen los tres


métodos antes declarados.

Parámetros Opcionales
Una utilidad muy potente agregada algunos años atrás es la posibilidad de que los parámetros
sean opcionales. Se trata de una forma más de sobrecarga, y se muestra su uso a continuación:
Declaración Descripción
Simplemente se hace asignándole el valor por
protected void Shot(int shotrate = 30) omisión al parámetro. La condición necesaria
{
⋮ es que siempre si hay varios parámetros a
} partir del primero opcional el resto de los
parámetros también deben ser opcionales.

Forma de uso Descripción


⋮ Cuando se llama a la función, se le puede o no pasar el
Shot(100);
Shot();
parámetro, tal como se muestra en los ejemplos
⋮ mostrados.

Ing. Gabriel Esquivel 55


IFTS18 Introducción a C# 2018
Propiedades
Desde fuera de la Clase (obviamente desde dentro también) al ser accedidas se parecen a
variables, pero en realidad una propiedad enmascara a 2 funciones (a veces llamadas el Getter
y Setter) que admiten código y vuelven a la propiedad mucho más poderosa que un mero
campo o variable.
Por ejemplo, en el caso de una Propiedad del tipo Integer, podría verificarse que la variable
solo tome valores acotados entre dos límites (por ejemplo entre 1 y 10), permitiendo generar
una excepción o enviar un mensaje en caso contrario.
Generalmente son de acceso público o interno, permitiendo que se vean externamente como
una variable inteligente o super variable.

Propiedades tradicionales o CLR


Las primeras propiedades en aparecer fueron las ahora denominadas propiedades CLR,
Formas de Declaración Descripción
Variable interna Ante todo se declara el campo que almacenará
finalmente el valor deseado, health en éste caso, con
protected int health; acceso limitado private o protected a lo sumo.
Luego se declara la propiedad en forma similar al de
public int Health { una variable, pero se incluyen las llaves principales, y
get las sub funciones get y set también con sus
{ propiedad
respectivas llaves.

return health; El bloque get indica donde comienza la lectura de la
} Variable variable miembro entera, en este caso health.
set Finalmente se retorna un objeto o valor haciendo uso
{
devuelta
if (health >= 0) de la palabra reservada return antes del nombre de
health = value; la variable a devolver.
else Para la asignación, el bloque o subfunción set indica

}
donde comienza el código de escritura de la variable
} entera, y utiliza la variable intermedia value, la cual
asignación
es un parámetro que contiene el valor del objeto que
se desea establecer.

Forma de uso Descripción


Imagínese que poseemos del algún modo de un objeto denominado
heroe que posee la propiedad antes vista Health. Si deseamos alterar
heroe.Health = 90; el valor de dicha propiedad simplemente accedemos a ella utilizando
el operador ".", y con notación de asignación de variables le damos el
valor deseado, en este caso 90.

Obviamente cualquiera que sepa programar un poco podría observar acertadamente que ¡no
existe aparentemente diferencias sustanciales entre la forma de uso mostrada de la propiedad
y por ejemplo una variable miembro publica! por ejemplo:
Forma de uso de la propiedad Forma de uso de la variable (debería cambiarse a publica)
heroe.Health = 90; item.health = 90;

Dejamos que el lector reflexione acerca del uso correcto de la primera e incorrecto en la
segunda, así como las ventajas y desventajas de cada una!

Ing. Gabriel Esquivel 56


IFTS18 Introducción a C# 2018
Read Only Property
Las propiedades de solo lectura solo cuentan con el sub bloque getter, como se aprecia
debajo:
Formas de Declaración Descripción
protected Texture2D textura; Esto resulta muy útil cuando el valor que toma la variable
public Texture2D Textura { solo depende del comportamiento interno del objeto,
get { como por ejemplo, la cantidad de Ítems que un Array
⋮ contiene, o si deseamos mostrar algo de información al
return textura;
mundo exterior, pero no permitimos que sea modificada
}
} externamente.

Auto propiedades
Como la mayoría de las propiedades involucran a una variable y al getter y setter sin más
código accesorio, en 2008 incluyeron esta variante de propiedades que permiten declarar lo
mismo con muchas menos palabras:
Formas de Declaración Descripción
En esencia se comportan como las propiedades CLR,
pero como podrá apreciar, la reducción de código es
public int Shield { get; set; }
significativa. En el caso de que necesite algún código de
verificación deberá recurrir a las propiedades CLR.
También son admisibles las autopropiedades de solo lectura y solo escritura, pero lo más
curioso son las que poseen getter y setter con distinto nivel de accesibilidad, por ejemplo:
Formas de Declaración Descripción
Como podrá deducir, el get es public,
accesible por cualquiera, pero el set es
public int Shield { get; protected set; }
protected, solo accesible desde dentro de
la clase o desde sus clases hijas.

Write Only Property


Las propiedades de solo escritura solo cuentan con la sub función set, e implícitamente5 se
pasa un parámetro denominado siempre value.
Formas de Declaración Descripción
public virtual int Health {
set Como podrá apreciar, en éste ejemplo antes de asignar el
{ valor a la variable miembro se verifica que el valor pasado
if (value >= 0) value sea mayor que cero (un valor de salud negativa no
health = value;
else
tiene sentido, no?), asignando el valor en el caso de que
health = 0; sea afirmativo, y estableciendo el valor 0 si value es
} negativo.
}

En la práctica es muy difícil encontrar ejemplos reales de propiedades de solo escritura, ya que
cuesta pensar que nunca se deseará leer el valor de dicha propiedad.

5
value es un parámetro implícito porque nunca fue declarado en ningún lugar del código, siendo quizás
una de las inconsistencias menores del C#, cosa que no se da en su lenguaje hermano en desuso Visual
Basic .Net, donde el parámetro es explicito.

Ing. Gabriel Esquivel 57


IFTS18 Introducción a C# 2018
Delegados
Se trata de un Tipo de dato muy especial, ya que lo que almacenan las variables de éste Tipo
son referencias a métodos, los cuales pueden ser ejecutados en cualquier momento a
voluntad.
Son análogos a los punteros a función en el lenguaje C, solo que son mucho más seguros de
utilizar, ya que en C se podía cometer el error de usar uno de éstos punteros por ejemplo con
Tipos de parámetros incorrectos, produciéndose entonces una excepción. En cambio, en .Net
el entorno se encarga de verificar los tipos y la cantidad de parámetros en tiempo de edición y
compilación.
Los pasos a seguir en el uso de delegados son:
 Declaración del tipo delegado, lo cual incluye la firma del método target
 Declaración de la variable del tipo delegado
 Inicialización de la variable, cargándola con una referencia al método Target elegido
 Ejecución del método Target desde la variable
Para representar la forma de operación de un delegado debajo se presenta un esquema
simplificado:
Figura 44. - Esquema de un Delegado, el método Target y la variable del Tipo Delegado

Clase que contiene


al método blanco
del delegado
Clase Target

public void metodotarget(int argumento1, object argumento2)

Método blanco (Target)


del delegado
Referencia al
Declaración del
método Target
delegado

Clase A

public delegate void tipodelegado(int argumento1, object argumento2);

tipodelegado variabledelegado; Declaración de la Variable


del Tipo delegado

En el esquema previo se aprecian dos clases, la primera contiene un método estándar sin
parámetros denominado metodotarget.
La segunda contiene la declaración del tipo delegado al cual se lo llamo tipodelegado y una
variable de dicho tipo llamada variabledelegado.
Solo restaría inicializar la variable variabledelegado con una referencia al método blanco
metodotarget.

Ing. Gabriel Esquivel 58


IFTS18 Introducción a C# 2018
Debajo se muestra al tipo delegado y a sus miembros:
Figura 45. Vista del la clase Delegate

Declaración de un Delegado
En la declaración de éstos se indica el formato de los métodos que pueden ser referenciados
(lo que a menudo se denomina firma o signature) y luego invocados, es decir, se indica el tipo
devuelto y los parámetros en cantidad, orden y Tipo. Se utiliza para ello la palabra reservada
delegate, como se muestra debajo:
Declaración

public delegate void delegado(int argumento1, object arguemento2);

Descripción
En éste caso hemos declarado un delegado de un método con 2 parámetros, el cual no
devuelve nada.

NOTA
Tenga presente que, la declaración de los delegados no están restringidas a estar
dentro de una clase, sino que pueden declararse también fuera de éstas.

Ing. Gabriel Esquivel 59


IFTS18 Introducción a C# 2018
Declaración de la variable Delegado
A continuación presentamos entre otras la declaración de la variable del Tipo del delegado
previamente especificado:
Uso
public class BackGround
{
public delegate void delegado(int argumento1, object arguemento2);

delegado variabledelegado;

public BackGround()
{
variabledelegado = metodotarget;
}

public void metodotarget(int argumento1, object arguemento2)


{
//Este es el método que se llamará, pero podría haber varios de
//estos métodos.
//target solo con la condición de que tenga la misma firma
}

public void disparar()


{
variabledelegado(10, this);
variabledelegado.Invoke(10, this);
}
}
Descripción
La variable será la referencia al método pasado en el constructor de la clase.
Además poseemos 1 método que se encarga de llamar o invocar al método referenciado en la
variable Var1 mediante el método Invoke miembro de System.Delegate.

NOTA
El ejemplo mostrado solo tiene fines didácticos y no está relacionado con el juego
utilizado para el resto de los ejemplos, ya que no tenía sentido usar delegados en
dicho juego.

Conclusión
La potencia real de los delegados radica en que, en general de antemano no se conoce cuál
será el método Target, pudiéndose entonces elegir cualquier método que cumpla las
condiciones
Además, es posible en la mayoría de los casos cambiar de método Target en tiempo de
ejecución.

Ing. Gabriel Esquivel 60


IFTS18 Introducción a C# 2018
Eventos
Funcionan como avisos para el mundo exterior indicando que algo ha sucedido dentro del
objeto que generó el evento.
Todos los objetos externos (o internos) que se han subscripto al evento se enterarán cuando
éste suceda, pudiendo entonces hacer algo al respecto.
Son totalmente asincrónicos, es decir, por lo general no se puede predecir cuando suceden.
Entre las interacciones entre objetos podemos mencionar:
 llamada directa a un método
 llamada indirecta a través de un delegado
 ejecución mediante captura de un evento
La siguiente ilustración muestra esto:
Figura 46. Objetos interactuando entre si.

Llamada directa a
método público

Objeto YY 1

Función Pública
expuesta
Objeto XX 1

Evento

Llamada a método Objeto XX 2


público/captura de Manejador de
evento Eventos

Ing. Gabriel Esquivel 61


IFTS18 Introducción a C# 2018
Generación Eventos
Los eventos en C# se declaran dentro de las clases en forma similar a los demás miembros, tal
como se muestra en el ejemplo siguiente:
Declaración
public partial class SpinWheel : UserControl
{
Public event EventHandler SpinFinished; Nombre del Evento

} Tipo
Descripción
Para declarar el Evento se utiliza el tipo delegado EventHandler y luego el nombre del evento.
EventHandler ya contiene la firma con los parámetros requeridos para pasar el evento.
Pero para disparar el evento se procede así:
Uso

if (SpinFinished != null)
{
SpinFinished(this, new EventArgs());
}

Descripción
En C# si hay alguien subscripto al evento se procede entonces a dispararlo. Para saber si hay un
subscripto, se pregunta con el if tal como se muestra. Si la variable SpinFinished no contiene
null, significa que alguien en algún lugar captura el evento.
El disparo del evento se parece mucho a llamar a un método. Aquí es donde hay que pasar los
parámetros requeridos:
 El primero es una referencia al objeto que lanzo el evento, con la palabra reservada
this.
 El segundo parámetro esta instanciado en el momento, y en esta ocasión no es muy
útil, ya que no se usa para nada… sin embargo, en otras ocasiones mediante herencia
es posible pasar información extra de quien lanza el evento a quien lo captura… por
ejemplo, las coordenadas en pantalla del cursor del mouse.

Ing. Gabriel Esquivel 62


IFTS18 Introducción a C# 2018

Figura 47. Miembros del Tipo EventHandler

Ing. Gabriel Esquivel 63


IFTS18 Introducción a C# 2018
Captura de Eventos
Existen básicamente dos formas de capturar eventos en C#, y ambas se describen a
continuación:

Captura de eventos mediante código en C#


Debajo aparece un ejemplo de uso de las mencionadas palabras reservadas:
Declaración
public SlotMachine()
{
item.SpinFinished += SpinFinished_rollo; Subscripción al Evento
}

private void SpinFinished_rollo(object sender, EventArgs e)


{

} Método que captura el Evento
Descripción
Aquí en el constructor de SlotMachine se puede apreciar cómo se subscribe para la captura de
un evento. En el podemos apreciar:
 item: es el objeto al cual capturamos su evento
 SpinFinished: es el evento al cual nos subscribimos para su captura
 +=: es el operador utilizado para subscribirse y capturar eventos en C#
 SpinFinished_rollo: es el nombre del método que captura el evento cuando éste
suceda
Debajo del constructor aparece el método ya mencionado, el cual se ejecutará cuando el
evento suceda.
Debajo se muestra cómo se pueden relacionar varios eventos con un único método:
Declaración
public SlotMachine()
{
item.SpinFinished += SpinFinished_rollo; Subscripción al Evento
item2.SomeEvent1 += SpinFinished_rollo;
item3.OtherEvent2 += SpinFinished_rollo;
}

private void SpinFinished_rollo(object sender, EventArgs e)


{

} Método que captura varios Eventos

Como podrá imaginar, la potencia de esto es increíble, ya que dinámicamente puedo suscribir
y eliminar la suscripción cuando lo desee.
Para dejar de capturar el evento hay que usar el operador -=.
Obviamente, si por error subscribo N veces un evento a un determinado método, cada vez
que el evento suceda el método será llamado también N veces.

Ing. Gabriel Esquivel 64


IFTS18 Introducción a C# 2018
Captura de Eventos en el Diseñador de WPF
La segunda forma requiere que sea en un formulario o control de WPF, en la vista diseño:
Declaración
<Window x:Class="WpfTragamonedas.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:WpfTragamonedas"
mc:Ignorable="d"
Title="MainWindow" Height="350" Width="525">
<Grid>
<Button Click="Button_Click" /> Subscripción al Evento
</Grid>
</Window>
Descripción
Arriba se puede observar el código típico de una aplicación de WPF, y en particular se ve como
se asocia el Evento Click del botón con el método Button_Click que lo captura.
Debajo se puede ver el código asociado al formulario y en particular el método que captura el
evento…
Código asociado
using System;
using System.Collections.Generic;
using System.Linq;

namespace WpfTragamonedas
{
/// <summary>
/// Lógica de interacción para MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}

private void Button_Click(object sender, RoutedEventArgs e)


{

}
} Método que captura el Evento
}

Ing. Gabriel Esquivel 65


IFTS18 Introducción a C# 2018

Controles Básicos
Figura 48. Vista del ToolBox
Para darle una mejor apariencia y funcionalidad a
nuestra aplicación procederemos a incluir algunos
controles.
Para ello debemos desplegar el Cuadro o Panel de
Herramientas (ToolBox) donde podremos
observar una gran variedad de controles
disponibles.
Entre los más simples y los más utilizados
tenemos:
 Label
 Button
 TextBox
 Calendar
 Image
 CheckBox
 StackPanel
 TextBlock
 ComboBox
 ListBox
 Grid

Inserción de Controles en un Formulario


Es una tarea muy simple, ya que solo hay que seleccionar con el ratón el control deseado para
luego dibujarlo con el ratón en el formulario.
Por ejemplo, seleccionando un TextBlock nos queda:
Figura 49. Vista de un TextBlock en el diseñador Como podrá ver, el
TextBlock posee un texto
por defecto que coincide
con su nombre, mientras
que las dimensiones de
éste son las dadas
durante la inserción con
el ratón. En la Imagen
también se puede
apreciar la forma del
ratón indicando que el
TextBlock puede ser
reposicionado y/o
redimensionado en el
formulario utilizando el
ratón.

Ing. Gabriel Esquivel 66


IFTS18 Introducción a C# 2018

Al dibujar o arrastrar el control al formulario se generará un código XML asociado a este, por
ejemplo:
Vista del código XML generado, asociado al TextBlock
<Window x:Class="WpfApplication1.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525">
<Grid>
<TextBlock HorizontalAlignment="Left" Margin="27,73,0,0"
TextWrapping="Wrap"
Text="TextBlock" VerticalAlignment="Top"/>
</Grid>
</Window>

Si cambiamos algunas de las propiedades del TextBlock, y agregamos un Button podemos


llegar a tener una aplicación como la mostrada abajo:
Figura 50. Formulario de ejemplo con dos controles

El código XML que debió agregarse para conseguir lo mostrado se observa debajo:
Código asociado al formulario
<Window x:Class="WpfTragamonedas.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:WpfTragamonedas"
mc:Ignorable="d"
Title="MainWindow" Height="350" Width="525">
<Grid>
<TextBlock Text="Hola, buen dia" Margin="10,17,42,131"
Background="#FF8DDA57" />
<Button Click="Button_Click" Content="Empezar" Margin="10,202,385,87" />
</Grid>
</Window>

Ing. Gabriel Esquivel 67


IFTS18 Introducción a C# 2018

Funcionalmente de momento no hace nada, pero permite mostrar como en muy poco tiempo
y con poco esfuerzo se puede lograr una aplicación con apariencia agradable al usuario final.

Jerarquía de Herencia de los Controles


Para empezar a trabajar con controles es importante saber que todos tienen una raíz común,
ya que heredan de una única clase denominada Control, y por lo tanto todos los controles
compartirán muchos de sus miembros.
En ella se han resaltado dos controles típicos, la clase Button y la clase Calendar, y se han
expandido las ramas del árbol que representan la Jerarquía de Herencia hasta la clase base
Control de los citados controles.
Figura 51. Vista del Explorador de Objetos con 2 controles comunes y sus arboles de herencia

Aquí también podemos ver al muy útil evento Click, que se puede apreciar en la Figura 51.,
junto a una descripción de la clase o miembro seleccionado.

Ing. Gabriel Esquivel 68


IFTS18 Introducción a C# 2018

Menús
La inclusión de un menú es simple, ya que se trata de un control más llamado simplemente
Menu.
Si hacemos Click sobre éste, luego lo dibujamos o arrastramos al formulario, y finalmente
agregamos los ítems del menú nos queda:
Figura 52. Vista del Menú agregado y sus sub items

Para ello, debimos escribir al menos éste código en el editor XML:


Código asociado al menú
<Grid>
<Menu Margin="0,0,0, 300">
<MenuItem Header="Archivo" >
<MenuItem Header="Nuevo" Click="MenuItem_Click"/>
<MenuItem Header="Abrir"/>
<MenuItem Header="Guardar"/>
</MenuItem>
</Menu>
<TextBlock Text="Hola, buen dia" Margin="10,24,42,131"
Background="#FF8DDA57" />
<Button Click="Button_Click" Content="Empezar" Margin="10,202,385,87" />
</Grid>

Como podrá observar, es sumamente fácil crear un menú con el diseñador. Ahora solo resta
agregar código para que algo suceda al presionar sobre la etiqueta del menú.
Para ello hacemos doble clic en la etiqueta deseada (en la primera en nuestro caso), entonces
el diseñador se encargará de crear el método asociado al clic de la etiqueta, lo que luce así:
Método que captura el clic sobre el ítem de menú Nuevo
private void MenuItem_Click(object sender, RoutedEventArgs e)
{

}

Ing. Gabriel Esquivel 69


IFTS18 Introducción a C# 2018

Cuadros de dialogo
Los cuadros de diálogo básicos están disponibles mediante código mediante la siguiente
sentencia:
Formas de Declaración
private void MenuItem_Click(object sender, RoutedEventArgs e)
{
if (MessageBox.Show("Desea continuar?",
"Atención!",
MessageBoxButton.OKCancel) == MessageBoxResult.OK)

} Falta algún código!!
Como resultado de ejecutar dicha línea obtenemos:
La sentencia pregunta por el resultado del cuadro de
Figura 53. Vista del MessageBox
diálogo (un valor del tipo MessageBoxResult que indica
el botón presionado, MessageBoxResult.OK o
MessageBoxResult.Cancel en este caso).
Tenga en cuenta que luego del if debe agregar código
para cuando el usuario acepta lo que indica este cuadro
de dialogo.

Ing. Gabriel Esquivel


23 de febrero de 2018
Versión 1.0.0.0

Ing. Gabriel Esquivel 70


IFTS18 Introducción a C# 2018

ANEXO 1
Debug Programming o Execution Time Programming
Una metodología de programación solo difundida entre algunos pocos es la Programación
durante la Depuración o Programación en Tiempo de Ejecución.
Mediante esta técnica se escribe código, generalmente solo el de algún algoritmo en
particular, el cual por lo general es algo complicado, y se hace durante la ejecución y
depuración del programa.
Esto en Visual Studio, en los lenguajes .Net es totalmente viable, ya que en tiempo de
ejecución este entorno permite editar el código fuente, borrando o agregando variables o
líneas al algoritmo deseado.
Entre las operaciones y herramientas que tenemos en tiempo de depuración podemos citar:

Ejecución paso a paso


Para ello se hace uso de los Breack Points, o puntos de Interrupción:
Figura 54. Breack Point e interrupción de la ejecución

Línea en ejecución

Breack Point

Como observará, tras presionar el botón button1 la ejecución del código se detiene en la
línea donde se halla el Breack Point (la línea actual en ejecución está toda marcada en
amarillo), permitiendo que el usuario inspeccione variables y tome decisiones sobre si el
código es correcto o se deben hacer modificaciones en éste.
En el siguiente grafico, el programador mueve el puntero a instrucción a otra línea, haciendo
que la del breack point no se ejecute:
Figura 55. Cambio del puntero a instrucción mediante el mouse

Breack Point

El usuario mueve el puntero a instrucción

Ing. Gabriel Esquivel 71


IFTS18 Introducción a C# 2018

Puntos de Interrupción
Se denominan puntos de interrupción o Breack Points a aquellos lugares específicos en las
líneas del código fuente donde la ejecución del programa se detendrá, condicional o
incondicionalmente, para que el programador inspeccione el código aledaño.
En la grafica anterior se presentó ya un punto de interrupción, marcado con un punto y la línea
de código en color marrón, pero la novedad aquí es un Panel que permite ver todos los Breack
Points así como su estado y estadísticas, tal como se aprecia a continuación:
Figura 56. Vista del Panel de Puntos de Interrupción

Observe que en este caso el último de los puntos de interrupción es condicional, es decir, que
solo bajo ciertas circunstancias detendrá la ejecución del código, en este caso cuando la
variable a sea menor que 10.
También es posible, mediante este panel, deshabilitar o habilitar los breack points a voluntad,
según las necesidades de depuración del momento.

Ing. Gabriel Esquivel 72


IFTS18 Introducción a C# 2018

Breack Points Condicionales


Para poder agregar dicha condición, hay que hacer clic con el botón derecho del ratón en el
punto de interrupción deseado, y cuando aparezca el menú contextual, seleccionar la opción
condición, como se muestra debajo:
Figura 57. Agregado de una condición a un Breack Point

Y, cuando aparezca el siguiente cuadro de dialogo completar la condición como se muestra a


continuación:
Figura 58. Cuadro de diálogo de condición para el Breack Point

Con esta condición solo se detendrá la ejecución mientras el valor de la variable a sea menor
que 10.

Ing. Gabriel Esquivel 73


IFTS18 Introducción a C# 2018

Edición en tiempo de Depuración


Es seguro una de las características sobresalientes del entorno, ya que permite que el
programador corrija errores de código, insertando o quitando líneas a su antojo, mientras el
programa se encuentra corriendo!
Esta tecnología no es nueva, sino que ya existía en el viejo VB 6.0, haciendo que crear o
corregir algoritmos complicados sea realmente una grata experiencia.
Para demostrar lo mencionado, a las líneas de código antes mostradas se le agregaron las
siguientes en tiempo de depuración, y se corrió paso a paso hasta la línea indicada:
Figura 59. Edición del Código durante la ejecución

Como verá, no solo se insertaron nuevas líneas, sino que se declaro una variable nueva, se
inserto un bucle, y se des comentó una línea antes comentada.

Revisión de los valores de las variables


Existen varias formas de revisar los valores de una variable y para todas ellas se puede utilizar
el ToolBar de Depuración, el cual se muestra a continuación:
Figura 60. Vista del ToolBar de Depuración

Entre los métodos y herramientas de revisión de variables tenemos:

Mediante el cursor
La forma más simple de chequear o ver el estado o valor de una variable es posicionándose
con el cursor sobre ésta, como se ve debajo:
Figura 61. Inspección de variables mediante el uso del cursor

Valor de a antes de ejecutarse la línea

Ing. Gabriel Esquivel 74


IFTS18 Introducción a C# 2018

Observe que la variable a se encuentra inicializada a 0, antes de ejecutarse dicha línea de


código.

Mediante el Panel Inmediato


El panel Inmediato es una importante herramienta de revisión de código, que utilizada como
una consola, permite escribir expresiones para chequear valores, o inclusive modificar valores.
Debajo se puede ver como con el signo de interrogación se consulta el valor numérico de la
variable a:
Figura 62. Inspección de variables mediante la Ventana Inmediato

Valor de a después de ejecutarse la línea

Para modificar el valor de una variable numérica o tipo string, solo es necesario escribir el
nombre de la variable, el signo igual = y el valor a asignar
También es posible ejecutar un método simplemente escribiendo la línea de código que llama
a ese método y presionar Enter.

Panel de Inspección
Muy similar al anterior, solo que se agrega a un listado en un panel que permite ver la
evolución de la variable cuando se ejecuta paso a paso. Debajo hay un ejemplo de dicha vista:
Figura 63. Uso del Panel de Inspección para la revisión de variables

Valor de a después de ejecutarse la línea

Variable fuera de contexto

Observe que junto a la variable a hay una segunda variable b que no se halla definida en el
contexto analizado (dentro de la función que se ejecuta).

Ing. Gabriel Esquivel 75


IFTS18 Introducción a C# 2018

Utilizando Vista Rápida


Haciendo clic con el botón derecho del mouse en una variable o tipo, despliega un menú
contextual, donde podemos elegir la opción Inspección rápida, como se muestra a
continuación:
Figura 64. Menú contextual y vista rápida

Lo mostrado en este caso es la siguiente ventana:


Figura 65. Vista del formulario de Inspección Rápida

Variable a inspeccionar

Tal como se ve, la variable, junto a su contenido público, variables y propiedades, puede
examinarse a voluntad, y a veces inclusive se puede modificar el valor de algunas de éstas.

Ing. Gabriel Esquivel 76


IFTS18 Introducción a C# 2018

También, donde aparecen Nodos extras en el árbol, es posible examinar los miembros del
objeto inspeccionado originalmente, como en este caso podría ser el button1 o el button2.

Mediante el Panel Automático


El panel automático no está siempre visible, pero aparece si desde el ToolBar de Depuración
hacemos clic en el botón para tal fin. Este panel, sin configuración previa muestra
automáticamente todas las variables y objetos del contexto actual de ejecución, como se
aprecia debajo:
Figura 66. Vista del Panel Automático

Valor de a después de ejecutarse la línea

Ing. Gabriel Esquivel 77

Você também pode gostar