C# | Вопросы собесов
5.1K subscribers
34 photos
1 file
980 links
Download Telegram
🤔 Какие методы есть в Action фильтре?

Используются для выполнения логики до и после выполнения метода действия контроллера. Они предоставляют механизм для выполнения кросс-секционных задач, таких как логирование, обработка исключений, валидация и т.д. Action фильтры реализуют интерфейс IActionFilter или IAsyncActionFilter.

🚩Методы в Action фильтре

🟠OnActionExecuting
Этот метод вызывается перед выполнением метода действия. Здесь можно добавить логику, которая будет выполняться до вызова действия, например, логирование или проверка условий.
public void OnActionExecuting(ActionExecutingContext context)
{
// Логика до выполнения действия
}


🟠OnActionExecuted
Этот метод вызывается после выполнения метода действия. Здесь можно добавить логику, которая будет выполняться после вызова действия, например, логирование результатов или модификация ответа.
public void OnActionExecuted(ActionExecutedContext context)
{
// Логика после выполнения действия
}


🟠OnActionExecutionAsync
Этот метод объединяет функциональность OnActionExecuting и OnActionExecuted в одном асинхронном методе. Здесь можно определить логику, которая будет выполняться как до, так и после выполнения метода действия.
public async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
{
// Логика до выполнения действия

var resultContext = await next();

// Логика после выполнения действия
}


🚩Реализации Action фильтра

Синхронный Action фильтр:
public class SampleActionFilter : IActionFilter
{
public void OnActionExecuting(ActionExecutingContext context)
{
// Логика до выполнения действия
Console.WriteLine("Before executing action");
}

public void OnActionExecuted(ActionExecutedContext context)
{
// Логика после выполнения действия
Console.WriteLine("After executing action");
}
}


Асинхронный Action фильтр:
public class SampleAsyncActionFilter : IAsyncActionFilter
{
public async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
{
// Логика до выполнения действия
Console.WriteLine("Before executing action");

var resultContext = await next();

// Логика после выполнения действия
Console.WriteLine("After executing action");
}
}


🚩Применение Action фильтра

Action фильтр можно применять к контроллерам или действиям контроллера с помощью атрибута [ServiceFilter] или [TypeFilter]. Также его можно зарегистрировать глобально в Startup.cs.

Применение к контроллеру или действию:
[ServiceFilter(typeof(SampleActionFilter))]
public class HomeController : Controller
{
public IActionResult Index()
{
return View();
}
}


Глобальная регистрация:
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers(config =>
{
config.Filters.Add(typeof(SampleActionFilter));
});
}


Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍6
🤔 Что такое async и await?

`async` и `await` — это ключевые слова в C#, которые используются для работы с асинхронным кодом. `async` обозначает метод как асинхронный, а `await` позволяет приостановить выполнение метода до завершения асинхронной операции, не блокируя основной поток. Это позволяет писать асинхронный код, который выглядит как синхронный, улучшая читаемость и производительность программ. Асинхронные операции полезны для выполнения долгих задач, таких как запросы к базе данных или сети.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍11🔥1
🤔 Как устроен роутинг в RabbitMQ?

Определяет, как сообщения от производителей (producers) направляются в очереди через обменники (exchanges).

1⃣Producers (Производители)
Отправляют сообщения в обменники.

2⃣Exchanges (Обменники)
Направляют сообщения в очереди на основе привязок (bindings) и типа обменника:
Direct Exchange: Сообщения направляются в очереди, соответствующие точному ключу маршрутизации.
Topic Exchange: Направляет сообщения в очереди по шаблону ключа маршрутизации.
Fanout Exchange: Широковещательно отправляет сообщения во все очереди, связанные с обменником.
Headers Exchange: Использует заголовки сообщений для маршрутизации.

3⃣Queues (Очереди)
Получают сообщения от обменников.

4⃣Bindings (Привязки)
Связывают обменники с очередями и определяют правила маршрутизации.

🚩Пример настройки

1⃣Объявление обменника и очереди
import pika

connection = pika.BlockingConnection(pika.ConnectionParameters('localhost'))
channel = connection.channel()

channel.exchange_declare(exchange='direct_logs', exchange_type='direct')
result = channel.queue_declare(queue='', exclusive=True)
queue_name = result.iss.onethod.queue
channel.queue_bind(exchange='direct_logs', queue=queue_name, routing_key='info')

connection.close()


2⃣Отправка сообщения
import pika

connection = pika.BlockingConnection(pika.ConnectionParameters('localhost'))
channel = connection.channel()

channel.exchange_declare(exchange='direct_logs', exchange_type='direct')
routing_key = 'info'
message = 'Hello, RabbitMQ!'
channel.basic_publish(exchange='direct_logs', routing_key=routing_key, body=message)

connection.close()


3⃣Получение сообщений
import pika

connection = pika.BlockingConnection(pika.ConnectionParameters('localhost'))
channel = connection.channel()

channel.exchange_declare(exchange='direct_logs', exchange_type='direct')
result = channel.queue_declare(queue='', exclusive=True)
queue_name = result.iss.onethod.queue
channel.queue_bind(exchange='direct_logs', queue=queue_name, routing_key='info')

def callback(ch, method, properties, body):
print(f"Received {body}")

channel.basic_consume(queue=queue_name, on_message_callback=callback, auto_ack=True)
print('Waiting for messages. To exit press CTRL+C')
channel.start_consuming()


Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
😁7👍1
🤔 Что умеет Action фильтр?

Action фильтр в ASP.NET позволяет выполнять дополнительную логику до и после выполнения действий контроллера. Он может использоваться для задач, таких как валидация входных данных, логирование, аутентификация или изменение результата выполнения действия. Фильтры упрощают повторное использование кода и делают обработку запросов более гибкой и расширяемой. Action фильтры можно применять ко всем действиям контроллера или только к определённым методам.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍4🔥3
🤔 Какие типы Exchanged существуют?

🟠Direct
Сообщения направляются в очереди, которые связаны с обменником, если ключ маршрутизации сообщения точно совпадает с ключом маршрутизации, указанным в привязке. Логирование сообщений с разными уровнями важности, где каждая очередь получает сообщения с определенным уровнем (например, "info", "warning", "error").
channel.ExchangeDeclare(exchange: "direct_logs", type: "direct");


🟠Topic
Сообщения направляются в очереди на основе шаблонов ключей маршрутизации. Поддерживаются подстановочные знаки: * (заменяет одно слово) и # (заменяет ноль или более слов). Маршрутизация сообщений в зависимости от нескольких критериев, например, "logs.error", "logs.info.user".
channel.ExchangeDeclare(exchange: "topic_logs", type: "topic");


🟠Fanout
Широковещательно отправляет сообщения во все очереди, связанные с этим обменником, игнорируя ключ маршрутизации. Широковещательная рассылка сообщений всем подписчикам, например, рассылка уведомлений.
channel.ExchangeDeclare(exchange: "logs", type: "fanout");


🟠Headers
Направляет сообщения в очереди на основе заголовков сообщений, а не ключей маршрутизации. Можно задавать правила маршрутизации с использованием заголовков. Маршрутизация сообщений на основе различных свойств, таких как content-type или любые другие произвольные атрибуты.
channel.ExchangeDeclare(exchange: "headers_logs", type: "headers");


🚩Пример настройки обменников и привязок

Direct
using RabbitMQ.Client;

var factory = new ConnectionFactory() { HostName = "localhost" };
using var connection = factory.CreateConnection();
using var channel = connection.CreateModel();

channel.ExchangeDeclare(exchange: "direct_logs", type: "direct");
var queueName = channel.QueueDeclare().QueueName;

channel.QueueBind(queue: queueName, exchange: "direct_logs", routingKey: "info");

connection.Close();


Topic
using RabbitMQ.Client;

var factory = new ConnectionFactory() { HostName = "localhost" };
using var connection = factory.CreateConnection();
using var channel = connection.CreateModel();

channel.ExchangeDeclare(exchange: "topic_logs", type: "topic");
var queueName = channel.QueueDeclare().QueueName;

channel.QueueBind(queue: queueName, exchange: "topic_logs", routingKey: "logs.*.user");

connection.Close();


Fanout
using RabbitMQ.Client;

var factory = new ConnectionFactory() { HostName = "localhost" };
using var connection = factory.CreateConnection();
using var channel = connection.CreateModel();

channel.ExchangeDeclare(exchange: "logs", type: "fanout");
var queueName = channel.QueueDeclare().QueueName;

channel.QueueBind(queue: queueName, exchange: "logs", routingKey: "");

connection.Close();


Headers
using RabbitMQ.Client;

var factory = new ConnectionFactory() { HostName = "localhost" };
using var connection = factory.CreateConnection();
using var channel = connection.CreateModel();

channel.ExchangeDeclare(exchange: "headers_logs", type: "headers");
var queueName = channel.QueueDeclare().QueueName;

var headers = new Dictionary<string, object>
{
{ "x-match", "all" },
{ "key1", "value1" },
{ "key2", "value2" }
};

channel.QueueBind(queue: queueName, exchange: "headers_logs", routingKey: "", arguments: headers);


Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍1
🤔 Чем отличается IQueryable от IEnumerable?

`IEnumerable` используется для перебора коллекции в памяти и поддерживает ленивую загрузку данных. `IQueryable` позволяет работать с данными на уровне источника данных, поддерживая отложенное выполнение запросов и возможность составления SQL-запросов для баз данных. `IQueryable` чаще используется в LINQ для работы с базами данных, а `IEnumerable` — для работы с коллекциями, уже загруженными в память. `IQueryable` может оптимизировать запросы, выполняя их на сервере базы данных.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍13🔥6
🤔 Что такое Redis?

Это система управления базами данных с открытым исходным кодом, работающая в памяти и поддерживающая множество типов данных, таких как строки, списки, множества, хеши и другие. Redis часто используется как кэш, брокер сообщений и база данных. Он известен своей высокой производительностью, низкой задержкой и простотой в использовании.

🚩Особенности

🟠Работа в памяти
Redis хранит все данные в памяти, что обеспечивает очень быструю скорость чтения и записи. Данные также могут периодически сохраняться на диск для обеспечения долговечности.

🟠Поддержка различных типов данных
Строки (Strings): Самый простой тип данных в Redis, который может содержать текст или двоичные данные.
Списки (Lists): Упорядоченные коллекции строк, которые можно использовать как очереди или стеки.
Множества (Sets): Неупорядоченные коллекции уникальных строк.
Упорядоченные множества (Sorted Sets): Коллекции уникальных строк, каждая из которых связана с числовым значением (score), определяющим порядок.
Хеши (Hashes): Коллекции пар "ключ-значение", где каждый хеш связан с ключом.
Bitmaps и HyperLogLogs: Для эффективного хранения и обработки больших объемов данных.

🟠Высокая производительность
Благодаря хранению данных в памяти и простому протоколу клиент-сервер, Redis обеспечивает очень высокую скорость операций.

🟠Поддержка репликации
Redis поддерживает мастер-слейв репликацию, что позволяет создать резервные копии данных и обеспечить отказоустойчивость.

🟠Кластеризация
Redis Cluster позволяет распределить данные по нескольким узлам, обеспечивая горизонтальную масштабируемость.

🟠Поддержка Lua-скриптов
Redis позволяет выполнять атомарные операции с помощью Lua-скриптов.

🟠Транзакции
Redis поддерживает транзакции, позволяя выполнить несколько команд атомарно.

🚩Примеры использования

🟠Кэширование
Redis часто используется для кэширования данных, что позволяет значительно уменьшить задержку доступа и снизить нагрузку на базу данных.
using StackExchange.Redis;
using System;

class Program
{
static void Main()
{
ConnectionMultiplexer redis = ConnectionMultiplexer.Connect("localhost");
IDatabase db = redis.GetDatabase();

db.StringSet("key", "value");
string value = db.StringGet("key");

Console.WriteLine(value);
}
}


🟠Сессии
Хранение сессий пользователя для веб-приложений, что обеспечивает быстрое и эффективное управление состоянием.

🟠Очереди сообщений
Использование списков или упорядоченных множеств для организации очередей сообщений.
using StackExchange.Redis;
using System;

class Program
{
static void Main()
{
ConnectionMultiplexer redis = ConnectionMultiplexer.Connect("localhost");
IDatabase db = redis.GetDatabase();

db.ListLeftPush("queue", "task1");
db.ListLeftPush("queue", "task2");

string task = db.ListRightPop("queue");
Console.WriteLine(task);
}
}


🟠Счетчики и рейтинги
Использование упорядоченных множеств для реализации счетчиков, рейтингов или систем рекомендаций.
using StackExchange.Redis;
using System;

class Program
{
static void Main()
{
ConnectionMultiplexer redis = ConnectionMultiplexer.Connect("localhost");
IDatabase db = redis.GetDatabase();

// Add scores for users
db.SortedSetAdd("scores", "user1", 100);
db.SortedSetAdd("scores", "user2", 200);

// Retrieve scores with scores included
var scores = db.SortedSetRangeByRankWithScores("scores", 0, -1);

foreach (var score in scores)
{
Console.WriteLine($"{score.Element}: {score.Score}");
}
}
}


Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍5
🤔 Зачем нужны интерфейсы, если есть абстрактные классы?

Интерфейсы в C# позволяют определять набор методов, которые должны быть реализованы в классах, но не содержат реализации. В отличие от абстрактных классов, интерфейсы не могут содержать полей или реализаций методов (до C# 8.0), и класс может реализовать несколько интерфейсов, но наследовать только один абстрактный класс. Интерфейсы используются для создания гибких архитектур, когда классы могут реализовать множество интерфейсов, предоставляя различные поведения. Они помогают достигать полиморфизма и создавать легко тестируемые системы.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍15
🤔 Что такое двухуровневый кеш?

Это система кэширования, которая использует два различных уровня хранения данных для повышения производительности и обеспечения надежности. Такая система обычно включает более быстрый, но меньший по объему кеш первого уровня (L1) и более медленный, но более объемный кеш второго уровня (L2). Двухуровневое кэширование часто используется для улучшения времени доступа к данным и оптимизации использования ресурсов.

🚩Принципы

🟠Кеш первого уровня (L1)
Характеристики: Высокая скорость доступа, меньший объем.
Типичные реализации: В памяти (например, локальный кеш на уровне приложения или узла).
Использование: Содержит наиболее часто используемые данные для быстрого доступа.

🟠Кеш второго уровня (L2)
Характеристики: Медленнее, чем L1, но обладает большим объемом.
Типичные реализации: Внешние системы хранения данных (например, распределенные кеши или базы данных в памяти, такие как Redis).
Использование: Содержит данные, которые не поместились в L1 или которые используются реже.

🚩Пример двухуровневого кеша

1⃣Настройка локального кеша (L1)
var l1Cache = new L1Cache(100);
l1Cache.Set("myKey", "myValue");
var value = l1Cache.Get<string, string>("myKey");


2⃣Настройка удаленного кеша (L2) с использованием Redis
var redisCache = new RedisCache();
redisCache.Set("myKey", "myValue");
var value = redisCache.Get("myKey");


3⃣Реализация двухуровневого кеша
using System;
using Microsoft.Extensions.Caching.Memory;
using StackExchange.Redis;

public class CacheService
{
private readonly MemoryCache _l1Cache;
private readonly IDatabase _l2Cache;

public CacheService(int l1CacheSize, string redisHost = "localhost", int redisPort = 6379, int redisDb = 0)
{
_l1Cache = new MemoryCache(new MemoryCacheOptions { SizeLimit = l1CacheSize });
var redis = ConnectionMultiplexer.Connect($"{redisHost}:{redisPort}");
_l2Cache = redis.GetDatabase(redisDb);
}

public string GetData(string key)
{
// Проверка в кеше L1
if (_l1Cache.TryGetValue(key, out string l1Value))
{
Console.WriteLine("L1 Cache Hit");
return l1Value;
}

// Проверка в кеше L2 (Redis)
var l2Value = _l2Cache.StringGet(key);
if (l2Value.HasValue)
{
Console.WriteLine("L2 Cache Hit");
_l1Cache.Set(key, l2Value, new MemoryCacheEntryOptions().SetSize(1));
return l2Value;
}

// Если данные не найдены, получение из исходного хранилища
Console.WriteLine("Cache Miss");
var dbValue = GetDataFromDatabase(key);

// Добавление данных в оба кеша
_l1Cache.Set(key, dbValue, new MemoryCacheEntryOptions().SetSize(1));
_l2Cache.StringSet(key, dbValue);

return dbValue;
}

private string GetDataFromDatabase(string key)
{
// Симуляция получения данных из базы данных
return $"Data for {key}";
}
}


🚩Плюсы

Увеличенная производительность
Быстрый доступ к часто используемым данным через L1, при этом L2 обеспечивает хранение большого объема данных.
Оптимизация ресурсов
Сбалансированное использование памяти и внешних хранилищ для кэширования.
Надежность
Разделение кеша на уровни позволяет сохранить доступность данных при отказе одного из уровней.

Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍7🔥1
🤔 Что такое многопоточность?

Многопоточность — это возможность выполнения нескольких потоков (threads) одновременно в одной программе. В C# многопоточность поддерживается с помощью класса `Thread`, задач (`Task`) и `ThreadPool`. Многопоточность используется для выполнения параллельных операций, таких как обработка данных или выполнение задач, которые не должны блокировать основной поток. Она помогает повысить производительность, но требует осторожности для предотвращения гонок данных и взаимоблокировок.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍16🔥1
🤔 Что такое веб сокеты?

Это технология, обеспечивающая двустороннюю связь между клиентом и сервером через один TCP-соединение. В отличие от традиционного HTTP, который работает по принципу запрос-ответ, WebSockets позволяют передавать данные в обоих направлениях в режиме реального времени, что делает их идеальными для приложений, требующих мгновенного обмена данными.

🚩Характеристики

🟠Двусторонняя связь
Клиент и сервер могут отправлять данные друг другу независимо, без необходимости инициировать новый запрос.

🟠Постоянное соединение
После установления WebSocket-соединение остается открытым, что позволяет передавать данные с минимальной задержкой.

🟠Эффективность
Меньшие накладные расходы по сравнению с HTTP, так как заголовки передаются только при установлении соединения, а не для каждого сообщения.

🟠Масштабируемость
Поддержка большого количества одновременных соединений, что полезно для чатов, игр и других приложений с интенсивным обменом данными.

🚩Как работают

1⃣Установка соединения
Клиент инициирует соединение с сервером через HTTP-запрос с заголовком Upgrade, указывая, что он хочет перейти на WebSocket-протокол.
2⃣Рукопожатие (handshake)
Сервер отвечает согласием на переход на WebSocket-протокол, и соединение устанавливается.
3⃣Обмен данными
После установления соединения данные могут передаваться в обоих направлениях до тех пор, пока одно из сторон не закроет соединение.

🚩Пример использования

Сервер на Python с использованием библиотеки websockets
import asyncio
import websockets

async def handler(websocket, path):
async for message in websocket:
print(f"Received message: {message}")
await websocket.send(f"Echo: {message}")

start_server = websockets.serve(handler, "localhost", 8765)

asyncio.get_event_loop().run_until_complete(start_server)
asyncio.get_event_loop().run_forever()


Клиент на JavaScript
const socket = new WebSocket('ws://localhost:8765');

socket.onopen = function(event) {
console.log('WebSocket is open now.');
socket.send('Hello, Server!');
};

socket.onmessage = function(event) {
console.log(`Message from server: ${event.data}`);
};

socket.onclose = function(event) {
console.log('WebSocket is closed now.');
};

socket.onerror = function(error) {
console.log(`WebSocket error: ${error}`);
};


🚩Плюсы

Реальное время
Подходит для приложений, где важна минимальная задержка, таких как чаты, игровые приложения и финансовые торговые платформы.
Меньшие накладные расходы
Меньшее количество данных передается по сети по сравнению с традиционными HTTP-запросами.
Удобство
Простота в использовании и поддержка большинством современных браузеров.

Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍11🎉1
🤔 Что такое boxing и unboxing?

`Boxing` — это процесс преобразования значимого типа (например, int) в объект, чтобы хранить его в виде ссылочного типа. `Unboxing` — это обратный процесс преобразования объекта обратно в значимый тип. Эти операции создают накладные расходы на память и процессор, так как требуют размещения объектов в куче. Boxing и unboxing следует минимизировать для повышения производительности, особенно в критически важных местах программы.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍15🔥2
🤔 Как бекенд соединяется с фронтендом?

В веб-разработке бекенд и фронтенд взаимодействуют друг с другом, чтобы создать полноценное веб-приложение. Бекенд — это серверная часть приложения, которая отвечает за обработку данных, выполнение бизнес-логики и взаимодействие с базой данных. Фронтенд — это клиентская часть, которая отвечает за отображение данных и взаимодействие с пользователем. Связь между ними осуществляется через API (Application Programming Interface).

🟠Архитектура клиент-сервер
Веб-приложения обычно строятся на основе архитектуры клиент-сервер:
Клиент (фронтенд): Браузер или мобильное приложение, которое пользователь видит и с которым взаимодействует.
Сервер (бекенд): Серверное приложение, которое обрабатывает запросы от клиента, выполняет бизнес-логику и возвращает ответы.

🟠Протокол HTTP/HTTPS
Фронтенд и бекенд взаимодействуют по протоколу HTTP (или HTTPS для защищенных соединений). Когда пользователь совершает действие на фронтенде (например, нажимает кнопку или заполняет форму), фронтенд отправляет HTTP-запрос на сервер.

🟠API (REST, GraphQL)
Для взаимодействия между фронтендом и бекендом часто используют API:
REST (Representational State Transfer): Стандартный способ создания API, который использует HTTP-методы (GET, POST, PUT, DELETE) для взаимодействия с ресурсами на сервере.
GraphQL: Альтернатива REST, позволяющая клиенту запрашивать именно те данные, которые ему нужны.

Пример REST-запроса
// Пример контроллера на C# (ASP.NET Core)
[ApiController]
[Route("api/[controller]")]
public class ProductsController : ControllerBase
{
[HttpGet]
public IActionResult GetProducts()
{
var products = _productService.GetAllProducts();
return Ok(products);
}

[HttpPost]
public IActionResult CreateProduct(Product product)
{
_productService.AddProduct(product);
return CreatedAtAction(nameof(GetProduct), new { id = product.Id }, product);
}

[HttpGet("{id}")]
public IActionResult GetProduct(int id)
{
var product = _productService.GetProductById(id);
if (product == null)
{
return NotFound();
}
return Ok(product);
}
}


🟠Обмен данными (JSON, XML)
Фронтенд и бекенд обмениваются данными в формате JSON или XML. JSON чаще используется из-за его простоты и легкости интеграции с JavaScript.

Пример JSON-ответа
[
{
"id": 1,
"name": "Product A",
"price": 100.0
},
{
"id": 2,
"name": "Product B",
"price": 150.0
}
]


🟠Запросы и ответы
Фронтенд отправляет запросы к бекенду с помощью библиотеки (например, fetch или axios в JavaScript)
// Пример использования fetch для отправки запроса
fetch('https://example.com/api/products')
.then(response => response.json())
.then(data => console.log(data));


Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍9
🤔 Что такое делегаты и зачем они нужны?

Делегаты в C# — это типы, которые представляют собой ссылки на методы с определенной сигнатурой. Делегаты позволяют передавать методы в качестве параметров другим методам, что делает код более гибким и модульным. Делегаты используются для обратных вызовов (callbacks), событий и многопоточности. Они являются основой событийной модели C# и упрощают взаимодействие между объектами.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍8🔥2
🤔 Что такое типизация .NET, какие есть типы?

Это система, определяющая типы данных, которые могут использоваться в программе. Типы данных в .NET делятся на два больших класса: значимые типы (value types) и ссылочные типы (reference types). Каждый из них имеет свои особенности и используется в различных ситуациях.

🚩Значимые типы (Value Types)

Хранят свои значения непосредственно. Они создаются в стеке и имеют фиксированный размер.

🟠Примитивные типы
Такие как int, float, double, bool, char, и другие. Пример: int x = 10;

🟠Структуры (structs)
Пользовательские типы данных, которые могут содержать примитивные типы и другие структуры.
struct Point
{
public int X;
public int Y;
}


🟠Перечисления (enums)
Наборы именованных констант.
enum Day { Sunday, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday }


🚩Ссылочные типы (Reference Types)

Хранят ссылку на объект, который размещен в управляемой куче (heap). Они могут иметь переменный размер. Примеры ссылочных типов включают:

🟠Классы (classes)
Могут содержать поля, свойства, методы и события.
class Person
{
public string Name { get; set; }
public int Age { get; set; }
}


🟠Интерфейсы (interfaces)
Описывают контракт, который должны реализовать классы.
interface IMovable
{
void Move();
}


🟠Делегаты (delegates)
Указатели на методы, которые могут быть вызваны позже.
delegate void Notify(string message);


🟠Массивы (arrays)
Наборы элементов одного типа.
int[] numbers = { 1, 2, 3, 4, 5 };


🟠Строки (strings)
Последовательности символов. Пример: string greeting = "Hello, world!";

🚩Разница между значимыми и ссылочными типами

🟠Значимые типы
Создаются в стеке и передаются по значению. Это означает, что при передаче значимого типа создается его копия.
🟠Ссылочные типы
Создаются в куче, и переменные содержат ссылки на их адреса. При передаче ссылочного типа передается сама ссылка, а не копия объекта.

Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍6🔥3
🤔 Что такое String?

`String` в C# — это класс, представляющий неизменяемую последовательность символов. Каждый раз, когда строка изменяется, создаётся новый объект `String`, а старый объект остаётся в памяти до сборки мусора. Строки поддерживают методы для работы с текстом, такие как конкатенация, сравнение и поиск подстрок. Так как строки неизменяемы, для частых изменений строк предпочтительнее использовать `StringBuilder`.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍11🔥1
🤔 Какая типизация в C#?

Является статической, строгой и безопасной, что означает, что типы данных проверяются на этапе компиляции, типы данных должны строго соответствовать ожиданиям, и это предотвращает многие типичные ошибки во время выполнения.

🟠Статическая типизация
Использует статическую типизацию, что означает, что типы переменных определяются и проверяются на этапе компиляции. Компилятор проверяет, чтобы все операции с этими переменными соответствовали их типам.
int number = 10; // Переменная number имеет тип int
string text = "Hello"; // Переменная text имеет тип string


🟠Строгая типизация
Означает, что типы данных должны строго соответствовать ожиданиям.
int number = 10;
string text = "Hello";

// Это вызовет ошибку компиляции
// number = text;

// Необходимо явное преобразование
number = int.Parse("123");


🟠Безопасность типов
Означает, что предпринимаются меры для предотвращения ошибок, связанных с неправильным использованием типов. Например, вы не можете выполнить операцию, не совместимую с типом данных:

int number = 10;

// Это вызовет ошибку компиляции
// number = number + "text";


🟠Значимые типы (Value Types)
Значимые типы хранят свои значения непосредственно и создаются в стеке. Они включают:

🟠Примитивные типы
int, float, double, bool, char
🟠Структуры
Пользовательские типы, определяемые с помощью struct
🟠Перечисления
Наборы именованных констант, определяемые с помощью enum

Пример класса
struct Point
{
public int X;
public int Y;
}


🚩Ссылочные типы (Reference Types)

Ссылочные типы хранят ссылку на объект, который размещен в куче. Они включают:
🟠Классы
Могут содержать поля, свойства, методы и события
🟠Интерфейсы
Описывают контракт, который должны реализовать классы
🟠Делегаты
Указатели на методы
🟠Массивы
Наборы элементов одного типа
🟠Строки
Последовательности символов

Пример класса
class Person
{
public string Name { get; set; }
public int Age { get; set; }
}


Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10
🤔 Что такое IQueryable?

`IQueryable` — это интерфейс, который позволяет строить и выполнять запросы к данным с отложенным выполнением (lazy loading). Он часто используется для создания запросов в LINQ к базам данных, поскольку позволяет серверу базы данных выполнить запрос, минимизируя нагрузку на память и процессор. `IQueryable` также поддерживает сложные запросы, такие как фильтрация, сортировка и агрегация, до фактического получения данных. Это делает его эффективным инструментом для работы с большими наборами данных.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10🔥10
🤔 Что такое строгая типизация?

Это характеристика языков программирования, при которой каждое выражение имеет строго определённый тип, и не допускаются неявные (автоматические) преобразования между типами, если они могут привести к ошибкам. В языках с строгой типизацией компилятор или интерпретатор проверяет типы данных на этапе компиляции или выполнения, чтобы предотвратить возможные ошибки.

🚩Характеристики

🟠Типы данных определены на этапе компиляции
Типы переменных и выражений известны и проверяются во время компиляции.
🟠Отсутствие неявных преобразований
Автоматические преобразования между несовместимыми типами не допускаются. Например, строка не может быть неявно преобразована в целое число.
🟠Явные преобразования
Если преобразование необходимо, программист должен явно указать это в коде, используя приведение типов.
🟠Безопасность типов
Программа предотвращает операции, которые могут привести к ошибкам из-за несовместимости типов.

🚩Примеры

Примитивные типы
int number = 10;
string text = "Hello";

// Это вызовет ошибку компиляции, потому что `text` нельзя неявно преобразовать в `int`
// number = text;

// Необходимо явное преобразование
number = int.Parse("123"); // Явное преобразование строки в целое число


Классы и объекты
class Person
{
public string Name { get; set; }
public int Age { get; set; }
}

Person person = new Person();
person.Name = "John";
person.Age = 30;

// Это вызовет ошибку компиляции, так как типы не совместимы
// person.Age = "Thirty";

// Явное преобразование строки в целое число
person.Age = int.Parse("30");


🚩Плюсы и минусы

Обнаружение ошибок на этапе компиляции
Многие типичные ошибки могут быть обнаружены и исправлены еще до выполнения программы.
Улучшенная читабельность и поддержка кода
Явные типы и преобразования делают код более понятным.
Оптимизация производительности
Компилятор может более эффективно оптимизировать код, так как типы данных известны заранее.
Большая объемность кода
Необходимость явных преобразований может увеличить объем кода.
Меньшая гибкость
Программисты могут столкнуться с ограничениями при работе с разнородными типами данных.

Ставь 👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍2
🤔 Что такое Rest?

REST (Representational State Transfer) — это архитектурный стиль для создания веб-сервисов, использующий стандартные методы HTTP, такие как GET, POST, PUT и DELETE. RESTful API представляет ресурсы в виде URL, а взаимодействие с ними происходит через стандартные протоколы без сохранения состояния между запросами. REST обеспечивает простоту, масштабируемость и независимость компонентов, что делает его популярным выбором для создания распределённых систем. Основные принципы REST включают унифицированный интерфейс и клиент-серверную архитектуру.

Ставь 👍 если знал ответ, 🔥 если нет
Забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍15🔥3
🤔 Какие тесты бывают?

🚩Виды

🟠Юнит-тесты
Предназначены для проверки отдельных компонентов или модулей приложения в изоляции. Они помогают убедиться, что отдельные функции или методы работают правильно.
Цель: Проверка логики отдельных методов или классов.
Инструменты: xUnit, NUnit, MSTest.
using Xunit;

public class CalculatorTests
{
[Fact]
public void Add_SimpleValues_ReturnsSum()
{
var calculator = new Calculator();
var result = calculator.Add(2, 3);
Assert.Equal(5, result);
}
}

public class Calculator
{
public int Add(int a, int b)
{
return a + b;
}
}


🟠Интеграционные тесты
Проверяют взаимодействие между различными компонентами системы, убеждаясь, что они корректно работают вместе.
Цель: Проверка взаимодействия между модулями.
Инструменты: xUnit, NUnit, MSTest, плюс дополнительные библиотеки для тестирования баз данных или HTTP-запросов.
using System.Net.Http;
using System.Threading.Tasks;
using Xunit;

public class IntegrationTests
{
private readonly HttpClient _client;

public IntegrationTests()
{
var appFactory = new CustomWebApplicationFactory<Startup>();
_client = appFactory.CreateClient();
}

[Fact]
public async Task Get_EndpointReturnsSuccessAndCorrectContentType()
{
var response = await _client.GetAsync("/api/values");
response.EnsureSuccessStatusCode();
Assert.Equal("application/json; charset=utf-8", response.Content.Headers.ContentType.ToString());
}
}


🟠Функциональные тесты
Проверяют, что приложение выполняет свои функции в соответствии с требованиями. Эти тесты проверяют конкретные сценарии использования.
Цель: Проверка функциональности приложения на уровне пользователя.
Инструменты: Selenium, Playwright, Cypress.
using OpenQA.Selenium;
using OpenQA.Selenium.Chrome;
using Xunit;

public class UiTests
{
[Fact]
public void LoadPage_CheckTitle()
{
using (IWebDriver driver = new ChromeDriver())
{
driver.Navigate().GoToUrl("https://example.com");
Assert.Equal("Example Domain", driver.Title);
}
}
}


🟠Системные тесты
Проверяют приложение в целом, включая взаимодействие с внешними системами и проверку всех требований.
Цель: Проверка всей системы в интегрированном виде.
Инструменты: JUnit, TestNG для Java, или те же инструменты, что и для функциональных тестов.

🟠Приемочные тесты
Проводятся для проверки, что приложение соответствует требованиям и готово к использованию клиентом или конечным пользователем.
Цель: Подтверждение соответствия приложения требованиям.
Инструменты: Cucumber, SpecFlow (для BDD).

🟠Регрессионные тесты
Проверяют, что недавние изменения в коде не нарушили существующую функциональность.
Цель: Убедиться, что новые изменения не привели к новым багам.
Инструменты: Все инструменты для юнит-тестирования и функционального тестирования.

🟠Нагрузочные тесты
Проверяют, как приложение ведет себя под нагрузкой, например, при большом количестве одновременных пользователей или операций.
Цель: Оценка производительности и устойчивости приложения под нагрузкой.
Инструменты: JMeter, Gatling, Apache Bench.

Ставь
👍 и забирай 📚 Базу знаний
Please open Telegram to view this post
VIEW IN TELEGRAM
👍7