Nota:
El acceso a esta página requiere autorización. Puede intentar iniciar sesión o cambiar directorios.
El acceso a esta página requiere autorización. Puede intentar cambiar los directorios.
Sugerencia
Este artículo forma parte de la sección Aspectos básicos de los desarrolladores que ya conocen al menos un lenguaje de programación y están aprendiendo C#. Si no está familiarizado con la programación, comience primero con los tutoriales de introducción .
¿Viene de otro idioma? La mayoría de los operadores de este artículo (, , , ||%/!&&!=*==, <, >, operadores de comparación y =) funcionan igual que en Java, C++y JavaScript. -+ Las principales sorpresas para los recién llegados son el comportamiento de división de enteros, la distinción de prefijo/postfijo para ++/--y la forma en que la asignación compuesta se convierte de nuevo al tipo de lado izquierdo.
Un operador combina uno o varios operandos en un solo valor. Ya conoces las expresiones y la precedencia de operadores en las expresiones de C#; este artículo profundiza más en los operadores específicos que usarás a diario.
Operadores aritméticos
Los cinco operadores aritméticos realizan cálculos numéricos.
| Operador | Name | Ejemplo | Result |
|---|---|---|---|
+ |
Adición | 10 + 3 |
13 |
- |
Resta | 10 - 3 |
7 |
* |
Multiplicación | 10 * 3 |
30 |
/ |
División | 10 / 3 |
3 |
% |
Resto | 10 % 3 |
1 |
int apples = 10;
int oranges = 3;
Console.WriteLine(apples + oranges); // => 13 (addition)
Console.WriteLine(apples - oranges); // => 7 (subtraction)
Console.WriteLine(apples * oranges); // => 30 (multiplication)
Console.WriteLine(apples / oranges); // => 3 (integer division: truncates toward zero)
Console.WriteLine(apples % oranges); // => 1 (remainder)
// Integer division always truncates toward zero — the fractional part is discarded
int result = 7 / 2;
Console.WriteLine(result); // => 3, not 3.5
// Truncation applies to negative results too: -7 / 2 is -3, not -4
int negResult = -7 / 2;
Console.WriteLine(negResult); // => -3
// To get a decimal result, at least one operand must be a double or float
double precise = 7.0 / 2;
Console.WriteLine(precise); // => 3.5
// Remainder with negative operands: the sign of the result matches the dividend
Console.WriteLine(-7 % 3); // => -1 (-7 = 3 × -2 + (-1))
Console.WriteLine(7 % -3); // => 1 ( 7 = -3 × -2 + 1)
La división de enteros se trunca hacia cero. Cuando ambos operandos son enteros, / descarta la parte fraccionarcional: 7 / 2 es 3, no 3.5. El truncamiento está hacia cero, no hacia el número más pequeño: -7 / 2 es -3 (no -4). Para obtener un resultado decimal, convierta al menos un operando en un tipo de punto flotante: 7.0 / 2 es 3.5. Esto difiere de algunos lenguajes en los que / siempre genera un resultado de punto flotante.
Resto (%) devuelve lo que queda después de la división de enteros: 10 % 3 es 1 porque 10 = 3 × 3 + 1. Resulta útil para recorrer un intervalo fijo (index % length), probar la divisibilidad (n % 2 == 0) y extraer dígitos. Con operandos negativos, el signo del resultado coincide con el signo del dividendo (el operando izquierdo): -7 % 3 es -1 y 7 % -3 es 1.
Operadores unarios
Los operadores unarios actúan sobre un único operando.
int temperature = 20;
int windChill = -5;
int heatIndex = +temperature; // unary +: value unchanged (rarely needed)
int coldFactor = -windChill; // unary -: negates the value → 5
Console.WriteLine(heatIndex); // => 20
Console.WriteLine(coldFactor); // => 5
bool isRaining = false;
bool isSunny = !isRaining; // logical NOT: flips true/false
Console.WriteLine(isSunny); // => True
-
+x(unario más) — deja el valor sin cambios; rara vez se escribe explícitamente, pero es válido. -
-x(unario menos): niega el valor. -
!x(NOT lógico): volteatrueafalseyfalseatrue. Usarás!a menudo:if (!list.Contains(item)).
Incremento y disminución
++ agrega 1 y -- resta 1. Ambos tienen un formato de prefijo y un formulario postfijo que difieren en qué valor se devuelve:
int counter = 5;
// Prefix: increment first, then use the new value
int a = ++counter;
Console.WriteLine(a); // => 6
Console.WriteLine(counter); // => 6
// Postfix: use the current value first, then increment
int b = counter++;
Console.WriteLine(b); // => 6 (value before increment)
Console.WriteLine(counter); // => 7 (incremented after)
// Decrement works the same way
int score = 10;
Console.WriteLine(score--); // => 10 (current value; score becomes 9)
Console.WriteLine(score); // => 9
-
Prefijo (
++i,--i): incrementa o disminuye primero la variable y, a continuación, devuelve el nuevo valor. -
Postfix (
i++, ): devuelve primero el valor actual y, a continuación,i--incrementa o disminuye la variable.
Cuando ++ o -- aparece como una instrucción independiente (no forma parte de una expresión mayor), el prefijo y el postfijo tienen el mismo efecto. La distinción solo importa cuando se usa el resultado, por ejemplo, en una asignación o como argumento de método.
Operadores relacionales
Los operadores relacionales comparan dos valores y devuelven un bool.
| Operador | Meaning | Ejemplo |
|---|---|---|
< |
Menor que | speed < limit |
> |
Mayor que | speed > limit |
<= |
Menor o igual que | score <= 100 |
>= |
Mayor o igual que | score >= 0 |
int speed = 75;
int limit = 60;
Console.WriteLine(speed > limit); // => True (greater than)
Console.WriteLine(speed < limit); // => False (less than)
Console.WriteLine(speed >= limit); // => True (greater than or equal)
Console.WriteLine(speed <= limit); // => False (less than or equal)
// Relational operators work on all numeric types and char
// char comparison uses the character's numeric Unicode code point, not alphabetical position
// 'B' (U+0042, value 66) is less than 'A' (U+0041, value 65)? No — 'A' (65) < 'B' (66)
char grade = 'B';
Console.WriteLine(grade >= 'A' && grade <= 'C'); // => True ('A'=65 <= 'B'=66 <= 'C'=67)
Los operadores relacionales funcionan en todos los tipos numéricos y char. Para char, la comparación usa el valor numérico de punto de código Unicode del carácter, no ningún orden alfabético o específico del dominio. En el ejemplo de grado anterior, 'B' es mayor o igual que 'A' porque 'B' tiene un valor Unicode 66 y 'A' tiene un valor Unicode 65: los números determinan la comparación, no el significado de las calificaciones de letra.
Operadores de igualdad
== y != compruebe si dos valores son iguales o no.
!= es true cuando los operandos no son iguales, y false cuando lo son.
int expected = 42;
int actual = 42;
Console.WriteLine(actual == expected); // => True (values are equal)
Console.WriteLine(actual != expected); // => False (true when values are not equal)
string name = "Alice";
Console.WriteLine(name == "Alice"); // => True (string content matches)
Console.WriteLine(name == "alice"); // => False (case-sensitive)
int x = 5;
Console.WriteLine(x == 10); // => False
Para los tipos numéricos y string, la igualdad comprueba los valores. Para los tipos de referencia, el valor predeterminado es identity (si dos variables apuntan al mismo objeto), pero muchos tipos incluidos string e record invalidan esto para comparar el contenido. Para obtener la imagen completa ( cómo funciona la igualdad entre tipos de valor, tipos de referencia, registros y estructuras), consulte Comparaciones de igualdad.
Nota:
C# no tiene un === operador . Escribir === es un error en tiempo de compilación:
// This does not compile — C# has no === operator
bool same = (x === 10);
Si procede de JavaScript, use == para la comparación de valores (C# == ya compara por valor para tipos primitivos y cadenas). Un error habitual relacionado es escribir accidentalmente = (asignación) cuando en realidad querías escribir == (comprobación de igualdad). El compilador detecta los formularios más comunes, pero comprueba de nuevo cualquier if condición que contenga =.
Operadores lógicos condicionales
&& (AND) y || (OR) combinan bool expresiones.
int age = 20;
bool hasTicket = true;
// && (AND): both sides must be true
bool canEnter = age >= 18 && hasTicket;
Console.WriteLine(canEnter); // => True
// || (OR): at least one side must be true
bool freeEntry = age < 5 || age >= 65;
Console.WriteLine(freeEntry); // => False
// Short-circuit: right side is skipped when the result is already determined
// Here, items.Count is never called if items is null
List<string>? items = null;
bool hasItems = items != null && items.Count > 0;
Console.WriteLine(hasItems); // => False (short-circuits; no NullReferenceException)
Ambos operadores cortocircuitan: dejan de evaluar el operando derecho cuando el resultado ya está determinado.
-
&&devuelvefalseen cuanto la parte izquierda esfalse. El lado derecho nunca se evalúa. -
||devuelvetrueen cuanto la parte izquierda estrue. El lado derecho nunca se evalúa.
El comportamiento de cortocircuito tiene una ventaja práctica: puede proteger de forma segura una operación en el lado derecho con una comprobación nula en el lado izquierdo, como se muestra en el ejemplo anterior. Si items es null, && se detiene ahí — nunca se llama a items.Count, por lo que no se produce ninguna excepción NullReferenceException.
Operador condicional ?:
El operador condicional (también denominado operador ternario ) evalúa una de las dos expresiones en función de una condición:
condition ? value-when-true : value-when-false
int temperature2 = 35;
// condition ? value-when-true : value-when-false
string weather = temperature2 > 30 ? "hot" : "comfortable";
Console.WriteLine(weather); // => hot
// Only the matching branch evaluates — the other branch is never run
int divisor = 0;
// The division 10 / divisor is never evaluated because divisor == 0 is true
int safe = divisor == 0 ? -1 : 10 / divisor;
Console.WriteLine(safe); // => -1
El ?: operador siempre evalúa exactamente una rama: el lado que no coincide con la condición nunca se evalúa. Esto hace que sea seguro usar una expresión en una de las partes que fallaría con otras entradas, siempre y cuando la condición la proteja correctamente.
Utilice ?: para opciones simples en línea. Para condiciones múltiples o bloques de código, suele ser más clara una instrucción if/else.
Operadores de asignación
El operador = de asignación simple almacena un valor en una variable:
int level = 1; // declaration + initialization
level = 5; // reassignment
La asignación en C# es asociativa por la derecha, lo que significa que a = b = c = 0 se evalúa de derecha a izquierda: c recibe 0, luego b recibe a y, después, 0 recibe 0.
Asignación compuesta
Los operadores de asignación compuesta combinan una operación binaria con la asignación:
| Operador | Equivalente a |
|---|---|
x += y |
x = x + y |
x -= y |
x = x - y |
x *= y |
x = x * y |
x /= y |
x = x / y |
x %= y |
x = x % y |
int level = 1;
level = 5; // simple assignment: replaces the value
Console.WriteLine(level); // => 5
// Compound assignment: short form of binary operation + assignment
int hp = 100;
hp += 20; // same as: hp = hp + 20
Console.WriteLine(hp); // => 120
hp -= 10; // same as: hp = hp - 10
Console.WriteLine(hp); // => 110
hp *= 2; // same as: hp = hp * 2
Console.WriteLine(hp); // => 220
hp /= 3; // same as: hp = hp / 3 (integer division)
Console.WriteLine(hp); // => 73
hp %= 7; // same as: hp = hp % 7
Console.WriteLine(hp); // => 3
La asignación compuesta es más que una forma abreviada. Evalúa el lado izquierdo exactamente una vez y, a continuación, convierte el resultado de nuevo en el tipo izquierdo. Esto importa cuando el lado izquierdo tiene efectos secundarios (como un indexador de array), y por eso la asignación compuesta en una variable byte se compila sin una conversión explícita, mientras que la forma desarrollada no:
// Assignment is right-associative: evaluated right to left
int a2, b2, c2;
a2 = b2 = c2 = 0; // c2 = 0 first, then b2 = 0, then a2 = 0
Console.WriteLine($"{a2} {b2} {c2}"); // => 0 0 0
// Compound assignment evaluates the left side once and converts back to the LHS type
byte small = 200;
small += 10; // equivalent to: small = (byte)(small + 10); result is 210
Console.WriteLine(small); // => 210
small += 10 se compila porque el compilador inserta automáticamente la conversión de restricción, el resultado, 210, se ajusta dentro del byte intervalo de 0 a 255.
small = small + 10 requeriría una conversión explícita (byte) , ya que la aritmética promueve ambos operandos a int.
Otros operadores de C#
En este artículo se tratan los operadores con los que te encontrarás con más frecuencia en el código del día a día. El lenguaje C# incluye más operadores útiles en escenarios específicos:
-
Operadores de desplazamiento (
<<,>>,>>>) : desplaza los bits de un valor entero de izquierda o derecha por un número especificado de posiciones. Operadores lógicos de bits y de enteros (&,|,^,~) — combinan o invierten valores enteros bit a bit, útiles en indicadores, máscaras y código de bajo nivel: Operadores de bits y de desplazamiento -
checkedyunchecked— controlan si el desbordamiento de enteros produce una excepción (checked) o se desborda silenciosamente (unchecked): checked y unchecked -
Operadores nulos (
??,??=,?.,?[]) — controlan de forma segura los valoresnullproporcionando valores predeterminados o interrumpiendo el acceso a miembros mediante cortocircuito: Operadores nulos -
Operadores de comprobación de tipos y de conversión (
is,as,typeof, conversión(T)) — comprueban o convierten el tipo en tiempo de ejecución de un valor: Operadores de comprobación de tipos y conversión -
Operadores de rango e índice (
..,^) : crear intervalos e índices relativos al final para segmentar matrices y intervalos: acceso de miembros y operadores condicionales NULL - Asignación de deconstrucción — descompone una tupla o un tipo en variables independientes en una sola expresión: Deconstrucción de tuplas y otros tipos
Véase también
- Expresiones de C# : cómo funcionan las expresiones y cómo funciona la precedencia del operador
-
Comparaciones de igualdad : cómo
==,!=yEqualsfuncionan en distintos tipos - Operadores y expresiones de C# (referencia de lenguaje): tabla de precedencia completa y cada operador