### ref
Позволяет передавать в метод ссылку на переменную, вместо значения. (Актуально для значимых типов)
При передачи ссылки, boxing не происходит. Просто передается адрес экземпляра значимого типа.
Использовать ref можно только для переменной, поля или элемента массива. Для свойства использовать нельзя.
Если передать в параметр с ref ссылочный тип, то на стек скопируется ссылка на ссылку. Например, если вы передадите в метод ссылочный тип, что хранился в поле, через ref, а затем присвоите переданной переменной null в методе, то поле вне метода также станет null.
Подробнее в [ролике](https://www.youtube.com/watch?v=rdkW4vOS0Xk&t=610s)
<br>
Определение метода
```csharp
private void RefEx(ref int value)
{
}
```
<br>
Вызов метода
```csharp
RefEx(ref value);
```
### out
То же самое, что и **ref**, только:
- Модификатор возвращает значение из метода, а не принимает в метод. Поэтому имеются такие требования:
- Параметр в методе нужно обязательно инициализировать (метод же должен что-то вернуть обратно)
В [русском stackoverflow](https://ru.stackoverflow.com/questions/480130/%d0%a7%d0%b5%d0%bc-out-%d0%be%d1%82%d0%bb%d0%b8%d1%87%d0%b0%d0%b5%d1%82%d1%81%d1%8f-%d0%be%d1%82-ref) есть объяснение разницы между out и ref
Определение метода
```csharp
public void OutEx(out int value)
{
// Нужно обязательно инициализировать переменную
value = 5;
}
```
Вызов метода
```csharp
OutEx(out value);
```
Можно объявить переменную прямо в параметре метода. Переменная будет доступна в текущей области видимости, где вызвали метод.
```csharp
OutEx(out var value);
```
### In
То же самое, что и **ref**, только:
- Доступен только для чтения
<br>
Определение метода
```csharp
public void InEx(in int value)
{
}
```
<br>
Вызов метода
```csharp
InEx(in value);
```
### params
Модификатор params в C# позволяет передавать переменное количество аргументов в метод. Это полезно, когда вы не знаете заранее, сколько аргументов будет передано, и хотите предоставить возможность вызвать метод с разным числом параметров.
Метод с модификатором params должен иметь только один параметр с этим модификатором, и он должен быть последним в списке параметров метода. Параметр с params должен быть массивом определенного типа.
- С модификатором **params** можно использовать только массив
Определение метода
```csharp
public void ParamsEx(params int[] values)
{
}
```
Определение метода с обязательным параметром.
Параметр с модификатором **params** нужно указывать после обязательных параметров.
```csharp
public void ParamsEx(string text, params float[] values)
{
}
```
Вызов метода
```csharp
//Можно ничего не передавать. По умолчанию будет пустым.
ParamsEx();
//
ParamsEx(1);
//Можно передать сколько угодно параметров
ParamsEx(1, 2);
//Можно передать просто массив
ParamsEx(new[] { 1, 2 });
//Метод с обязательным параметром
ParamsEx("Cat", 1, 2, 3);
```
### default
Параметрам метода можно назначать значения по умолчанию (дефолтные)
Определение метода
```csharp
public void DefaultEx(int value = 0)
{
}
```
Обязательные параметры указываются перед дефолтными
```csharp
public void DefaultEx(string name, int value = 0)
{
}
```
Дефолтных параметров может быть несколько
```csharp
public void DefaultEx2(string name, int age = 20, int value2 = 0)
{
}
```
<br>
Вызов метода.
Можем ничего не передавать.
```csharp
DefaultEx();
```
Можно перепрыгнуть через дефолтный параметр и указать значение только для другого дефолтного.
```csharp
DefaultEx2(name: "Kate", value2: 99);
```