Паттерны проектирования (или шаблоны проектирования) — это проверенные решения общих проблем, которые возникают при разработке программного обеспечения. Они представляют собой шаблоны для организации кода, которые улучшают его структуру, читаемость и повторное использование. Паттерны проектирования не являются готовым кодом, но они предлагают структуры и подходы, которые можно адаптировать к конкретным потребностям проекта.
Обеспечивает создание единственного экземпляра класса и предоставляет глобальную точку доступа к этому экземпляру.
public class Singleton
{
private static Singleton instance;
private Singleton() { }
public static Singleton Instance
{
get
{
if (instance == null)
{
instance = new Singleton();
}
return instance;
}
}
}
Определяет интерфейс для создания объекта, но позволяет подклассам изменить тип создаваемого объекта.
public abstract class Product { }
public class ConcreteProductA : Product { }
public class ConcreteProductB : Product { }
public abstract class Creator
{
public abstract Product FactoryMethod();
}
public class ConcreteCreatorA : Creator
{
public override Product FactoryMethod()
{
return new ConcreteProductA();
}
}
public class ConcreteCreatorB : Creator
{
public override Product FactoryMethod()
{
return new ConcreteProductB();
}
}Позволяет объектам с несовместимыми интерфейсами работать вместе.
public interface ITarget
{
void Request();
}
public class Adaptee
{
public void SpecificRequest()
{
Console.WriteLine("Specific request");
}
}
public class Adapter : ITarget
{
private readonly Adaptee _adaptee;
public Adapter(Adaptee adaptee)
{
_adaptee = adaptee;
}
public void Request()
{
_adaptee.SpecificRequest();
}
}
Определяет зависимость "один ко многим" между объектами таким образом, что при изменении состояния одного объекта все зависимые объекты оповещаются и обновляются автоматически.
public interface IObserver
{
void Update();
}
public class ConcreteObserver : IObserver
{
public void Update()
{
Console.WriteLine("Observer updated");
}
}
public class Subject
{
private readonly List<IObserver> observers = new List<IObserver>();
public void Attach(IObserver observer)
{
observers.Add(observer);
}
public void Detach(IObserver observer)
{
observers.Remove(observer);
}
public void Notify()
{
foreach (var observer in observers)
{
observer.Update();
}
}
}
Паттерны проектирования — это проверенные решения общих проблем в разработке программного обеспечения. Они делятся на три категории: порождающие (Singleton, Factory Method), структурные (Adapter, Composite) и поведенческие (Observer, Strategy). Использование паттернов улучшает структуру кода, делает его более читаемым и гибким.
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥3😁1
Anonymous Quiz
81%
Action, Func, Predicate.
5%
List, Array, Dictionary.
9%
Event, Property, Method.
5%
Static, Virtual, Override.
Паттерны проектирования — это шаблоны для решения общих проблем при разработке ПО. Они делятся на три категории:
Паттерны проектирования (порождающие, структурные, поведенческие) — это шаблоны для решения типовых задач в разработке ПО, улучшающие структуру и гибкость кода.
Please open Telegram to view this post
VIEW IN TELEGRAM
👍3
Anonymous Quiz
48%
Использовать generics.
10%
Использовать boxing.
13%
Использовать массивы.
29%
Использовать структуры.
🤯3
Монолитная и микросервисная архитектуры представляют собой два разных подхода к построению программных систем. Рассмотрим ключевые отличия между ними на практике:
Определение:
Монолитная архитектура представляет собой единое, цельное приложение, в котором все компоненты и модули тесно связаны друг с другом.
Особенности:
Определение:
Микросервисная архитектура разделяет приложение на множество небольших, независимых сервисов, каждый из которых выполняет свою конкретную задачу.
Особенности:
Монолит:
Предположим, у вас есть интернет-магазин. В монолитной архитектуре все функции, такие как каталог товаров, корзина, заказы, учетные записи пользователей и платежи, находятся в одном приложении. Обновление логики корзины требует развертывания всего приложения заново.
Микросервисы:
В микросервисной архитектуре каждый компонент интернет-магазина становится отдельным сервисом. Есть отдельные сервисы для каталога товаров, корзины, заказов, учетных записей пользователей и платежей. Если нужно обновить логику корзины, вы можете развернуть только соответствующий сервис, не затрагивая остальные.
Монолитная архитектура объединяет все компоненты приложения в одном проекте, что упрощает разработку и деплой, но усложняет масштабирование и поддержку. Микросервисная архитектура разделяет приложение на независимые сервисы, что улучшает масштабируемость и модульность, но усложняет координацию и тестирование.
Please open Telegram to view this post
VIEW IN TELEGRAM
👍2😁1
Anonymous Quiz
4%
Использовать команды для переноса данных вручную.
14%
Использовать SQL скрипты.
78%
Использовать систему миграций.
4%
Использовать внешние ключи.
СиШарпСНуляДоПрофи.docx
88.2 MB
Парень написал обширное руководство по C# в виде формата Word, которое охватывает все основные концепции языка С# включая парадигму ООП.
Руководство еще подлежит коррективам но вы сможете уже его использовать для обучения/ознакомления и зафиксировать основные моменты. Сам документ прикреплен ниже. Выглядит очень информативно 👍
Можете оставить фидбек в коментах, ну либо кто хочет помочь совместно закончить реализацию напишите ему: https://t.iss.one/vlar4x
Руководство еще подлежит коррективам но вы сможете уже его использовать для обучения/ознакомления и зафиксировать основные моменты. Сам документ прикреплен ниже. Выглядит очень информативно 👍
Можете оставить фидбек в коментах, ну либо кто хочет помочь совместно закончить реализацию напишите ему: https://t.iss.one/vlar4x
🔥8
Внешние ключи в базе данных играют важную роль в обеспечении целостности данных и установлении связей между таблицами. Они представляют собой специальные столбцы или группы столбцов в одной таблице, которые ссылаются на первичный ключ другой таблицы. Рассмотрим подробнее, почему внешние ключи важны и как они должны использоваться.
Orders и таблица Customers, внешний ключ в Orders может ссылаться на первичный ключ в Customers, гарантируя, что каждый заказ относится к существующему клиенту.Orders, если нет соответствующего клиента в таблице Customers.ALTER TABLE.CREATE TABLE Orders (
OrderID int PRIMARY KEY,
OrderDate datetime,
CustomerID int,
FOREIGN KEY (CustomerID) REFERENCES Customers(CustomerID)
);
ALTER TABLE.ALTER TABLE Orders
ADD CONSTRAINT FK_CustomerOrder
FOREIGN KEY (CustomerID) REFERENCES Customers(CustomerID);
CREATE TABLE Orders (
OrderID int PRIMARY KEY,
OrderDate datetime,
CustomerID int,
FOREIGN KEY (CustomerID) REFERENCES Customers(CustomerID)
ON DELETE CASCADE
);
CREATE TABLE Customers (
CustomerID int PRIMARY KEY,
CustomerName varchar(255)
);
CREATE TABLE Orders (
OrderID int PRIMARY KEY,
OrderDate datetime,
CustomerID int,
FOREIGN KEY (CustomerID) REFERENCES Customers(CustomerID)
);
CREATE TABLE Orders (
OrderID int PRIMARY KEY,
OrderDate datetime,
CustomerID int,
FOREIGN KEY (CustomerID) REFERENCES Customers(CustomerID)
ON DELETE CASCADE
);
Внешние ключи должны быть в базе данных для поддержания целостности данных, установления связей между таблицами и упрощения запросов. Они предотвращают некорректные данные и обеспечивают правильные каскадные операции при обновлениях и удалениях.
Please open Telegram to view this post
VIEW IN TELEGRAM
Anonymous Quiz
91%
DbContext, DbSet, LINQ to Entities.
5%
DataTable, DataSet, DataRow.
2%
Collection, List, Array.
2%
Index, Key, Value.
🤯2
Покрытие кода контроллера тестами является важной практикой, которая помогает повысить качество и надежность приложения. Рассмотрим, что это означает, зачем это нужно, и как это делается.
Тесты для контроллеров — это автоматические тесты, которые проверяют функциональность методов контроллеров в веб-приложениях. Эти тесты могут быть двух основных типов:
Модульные тесты контроллеров проверяют методы контроллера изолированно. Для этого обычно используются моки или заглушки для зависимостей контроллера, таких как сервисы или репозитории.
Пример модульного теста контроллера с использованием библиотеки xUnit и Moq:
using Moq;
using Xunit;
using MyWebApp.Controllers;
using MyWebApp.Services;
using Microsoft.AspNetCore.Mvc;
public class MyControllerTests
{
[Fact]
public void Get_ReturnsOkResult_WithListOfItems()
{
// Arrange
var mockService = new Mock<IMyService>();
mockService.Setup(service => service.GetItems()).Returns(new List<string> { "Item1", "Item2" });
var controller = new MyController(mockService.Object);
// Act
var result = controller.Get();
// Assert
var okResult = Assert.IsType<OkObjectResult>(result);
var items = Assert.IsType<List<string>>(okResult.Value);
Assert.Equal(2, items.Count);
}
}
Интеграционные тесты проверяют взаимодействие контроллера с другими компонентами системы. Обычно для таких тестов используется реальная база данных или её тестовый аналог.
Пример интеграционного теста с использованием xUnit и TestServer из Microsoft.AspNetCore.TestHost:
using System.Net.Http;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc.Testing;
using Xunit;
public class MyControllerIntegrationTests : IClassFixture<WebApplicationFactory<MyWebApp.Startup>>
{
private readonly HttpClient _client;
public MyControllerIntegrationTests(WebApplicationFactory<MyWebApp.Startup> factory)
{
_client = factory.CreateClient();
}
[Fact]
public async Task Get_ReturnsOkResult_WithListOfItems()
{
// Act
var response = await _client.GetAsync("/api/my");
// Assert
response.EnsureSuccessStatusCode();
var responseString = await response.Content.ReadAsStringAsync();
Assert.Contains("Item1", responseString);
}
}
Покрытие кода контроллера тестами помогает обнаруживать ошибки, поддерживать корректность кода, облегчает рефакторинг и улучшает архитектуру приложения. Модульные тесты проверяют методы изолированно, а интеграционные тесты проверяют их взаимодействие с другими компонентами.
Please open Telegram to view this post
VIEW IN TELEGRAM
❤1
Anonymous Quiz
82%
List, Dictionary, Queue, Stack.
11%
Array, Hashtable, SortedList, LinkedList.
7%
Collection, Set, Map, Queue.
1%
Tree, Graph, Map, Set.
😁5
В трехслойной архитектуре (трехуровневая архитектура), также известной как многоуровневая архитектура, приложения разделяются на три логических слоя:
REST (Representational State Transfer):
С точки зрения трехслойной архитектуры:
SWAP (Simple Web API):
С точки зрения трехслойной архитектуры:
В трехслойной архитектуре REST и SWAP выступают как интерфейсы, обеспечивающие взаимодействие между слоями, при этом они сами чаще всего принадлежат к логическому слою, поскольку реализуют бизнес-логику и правила приложения, обеспечивая доступ к данным через слой данных и предоставляя функционал презентационному слою.
Please open Telegram to view this post
VIEW IN TELEGRAM
❤1
Anonymous Quiz
98%
async, await.
1%
parallel, concurrent.
0%
thread, lock.
1%
task, event.
🤯4
Паттерны Adapter и Decorator оба являются структурными паттернами, которые помогают управлять взаимодействием между объектами. Однако, они решают разные задачи и применяются в различных контекстах. Рассмотрим каждый из этих паттернов подробнее и сравним их.
Описание:
Цель:
Применение:
Пример:
// Существующий класс с несовместимым интерфейсом
public class LegacyPrinter
{
public void PrintLegacy(string text)
{
Console.WriteLine("Legacy print: " + text);
}
}
// Целевой интерфейс, который ожидает клиент
public interface IPrinter
{
void Print(string text);
}
// Адаптер, который приводит интерфейс LegacyPrinter к интерфейсу IPrinter
public class PrinterAdapter : IPrinter
{
private readonly LegacyPrinter _legacyPrinter;
public PrinterAdapter(LegacyPrinter legacyPrinter)
{
_legacyPrinter = legacyPrinter;
}
public void Print(string text)
{
_legacyPrinter.PrintLegacy(text);
}
}
// Использование адаптера
public class Client
{
public void ClientCode(IPrinter printer)
{
printer.Print("Hello, World!");
}
}
var legacyPrinter = new LegacyPrinter();
var adapter = new PrinterAdapter(legacyPrinter);
var client = new Client();
client.ClientCode(adapter);
Описание:
Цель:
Пример:
// Базовый интерфейс
public interface INotifier
{
void Send(string message);
}
// Конкретный компонент
public class EmailNotifier : INotifier
{
public void Send(string message)
{
Console.WriteLine("Sending Email: " + message);
}
}
// Базовый декоратор
public class NotifierDecorator : INotifier
{
private readonly INotifier _wrappee;
public NotifierDecorator(INotifier notifier)
{
_wrappee = notifier;
}
public virtual void Send(string message)
{
_wrappee.Send(message);
}
}
// Конкретный декоратор
public class SMSNotifier : NotifierDecorator
{
public SMSNotifier(INotifier notifier) : base(notifier) { }
public override void Send(string message)
{
base.Send(message);
Console.WriteLine("Sending SMS: " + message);
}
}
// Использование декоратора
var emailNotifier = new EmailNotifier();
var smsNotifier = new SMSNotifier(emailNotifier);
smsNotifier.Send("Hello, World!");
Паттерн Adapter преобразует интерфейс одного класса к интерфейсу, ожидаемому клиентом, что позволяет несовместимым объектам работать вместе. Паттерн Decorator динамически добавляет новые обязанности объекту, оборачивая его, и предоставляет гибкую альтернативу наследованию для расширения функциональности. Adapter используется для приведения интерфейсов в соответствие, а Decorator — для расширения возможностей объектов.
Please open Telegram to view this post
VIEW IN TELEGRAM
Anonymous Quiz
97%
DateTime, TimeSpan.
1%
Calendar, Clock.
2%
Timestamp, Stopwatch.
0%
Period, Interval.
👍1🤔1
Паттерн проектирования Factory (Фабрика) — это порождающий паттерн, который предоставляет интерфейс для создания объектов в суперклассе, но позволяет подклассам изменять тип создаваемых объектов. Основная идея заключается в том, чтобы вынести создание объектов из кода, который их использует, в отдельный компонент или метод. Это помогает уменьшить зависимость кода от конкретных классов и улучшить его гибкость и расширяемость.
public class SimpleFactory
{
public IProduct CreateProduct(string type)
{
if (type == "A")
return new ProductA();
else if (type == "B")
return new ProductB();
else
throw new ArgumentException("Unknown product type.");
}
}
public abstract class Creator
{
public abstract IProduct FactoryMethod();
}
public class ConcreteCreatorA : Creator
{
public override IProduct FactoryMethod()
{
return new ProductA();
}
}
public class ConcreteCreatorB : Creator
{
public override IProduct FactoryMethod()
{
return new ProductB();
}
}
Паттерн Factory позволяет абстрагировать процесс создания объектов, уменьшая зависимость от конкретных классов и улучшая гибкость и расширяемость кода. Он включает такие разновидности, как простая фабрика, фабричный метод и абстрактная фабрика, каждая из которых решает свои специфические задачи по созданию объектов.
Please open Telegram to view this post
VIEW IN TELEGRAM
👍1
Anonymous Quiz
86%
Преобразование объектов в поток байтов и обратно.
5%
Сжатие данных и их восстановление.
6%
Шифрование и дешифрование данных.
4%
Конвертация строк в числа и обратно.
В современном C# паттерн Singleton можно реализовать несколькими способами, каждый из которых имеет свои преимущества и предназначен для различных сценариев использования. Рассмотрим несколько распространенных подходов к реализации Singleton.
Ленивый Singleton инициализируется при первом обращении. Это обеспечивает отложенную инициализацию объекта и гарантирует потокобезопасность.
Пример:
public class Singleton
{
private static readonly Lazy<Singleton> lazyInstance = new Lazy<Singleton>(() => new Singleton());
public static Singleton Instance => lazyInstance.Value;
private Singleton()
{
// Приватный конструктор
}
}
Lazy<T> позволяет легко и безопасно реализовать отложенную инициализацию.Этот подход использует
lock для обеспечения потокобезопасности при создании экземпляра.Пример:
public class Singleton
{
private static Singleton instance;
private static readonly object lockObj = new object();
private Singleton()
{
// Приватный конструктор
}
public static Singleton Instance
{
get
{
if (instance == null)
{
lock (lockObj)
{
if (instance == null)
{
instance = new Singleton();
}
}
}
return instance;
}
}
}
lock, проверяя instance дважды.Экземпляр Singleton создается при загрузке класса. Это гарантирует потокобезопасность за счет особенностей инициализации статических переменных в .NET.
Пример:
public class Singleton
{
private static readonly Singleton instance = new Singleton();
public static Singleton Instance => instance;
private Singleton()
{
// Приватный конструктор
}
}
Использование статического конструктора для инициализации Singleton.
Пример:
public class Singleton
{
private static readonly Singleton instance;
static Singleton()
{
instance = new Singleton();
}
public static Singleton Instance => instance;
private Singleton()
{
// Приватный конструктор
}
}
В современных приложениях, особенно с использованием ASP.NET Core, Singleton часто регистрируется в контейнере внедрения зависимостей.
Пример:
public class SingletonService
{
public void DoWork()
{
// Выполнение работы
}
}
// Регистрация в контейнере служб
public void ConfigureServices(IServiceCollection services)
{
services.AddSingleton<SingletonService>();
}
// Использование в контроллере
public class MyController : ControllerBase
{
private readonly SingletonService _singletonService;
public MyController(SingletonService singletonService)
{
_singletonService = singletonService;
}
public IActionResult Index()
{
_singletonService.DoWork();
return Ok();
}
}
В C# паттерн Singleton реализуется с использованием различных подходов: ленивой инициализации (с
Lazy<T>), потокобезопасного двойного блокирования, инициализации при загрузке класса и статического конструктора. В современных приложениях также используется внедрение зависимостей (DI), особенно в ASP.NET Core, для обеспечения единственного экземпляра.Please open Telegram to view this post
VIEW IN TELEGRAM
🔥5👍2
Anonymous Quiz
99%
Блоками try, catch, finally.
1%
Методами include, require.
1%
Операторами check, uncheck.
0%
Командами start, end.
❤1
public class BaseClass
{
public virtual void DoWork() { /* базовое поведение */ }
}
public class DerivedClass : BaseClass
{
public override void DoWork() { /* расширенное поведение */ }
}
public interface IWork
{
void DoWork();
}
public class MyClass : IWork
{
public void DoWork() { /* реализация интерфейса */ }
}
public class BaseClass
{
public virtual void DoWork() { /* базовое поведение */ }
}
public class Decorator : BaseClass
{
private BaseClass _base;
public Decorator(BaseClass baseClass) { _base = baseClass; }
public override void DoWork()
{
_base.DoWork();
// Добавленное поведение
}
}
public interface ITarget
{
void Request();
}
public class Adaptee
{
public void SpecificRequest() { /* специальное поведение */ }
}
public class Adapter : ITarget
{
private Adaptee _adaptee = new Adaptee();
public void Request() { _adaptee.SpecificRequest(); }
}
public static class Extensions
{
public static void NewMethod(this ExistingClass obj)
{
// Добавленное поведение
}
}
Поведение классов в C# можно расширить через наследование, интерфейсы, паттерн декоратор, адаптер и расширяющие методы.
Please open Telegram to view this post
VIEW IN TELEGRAM
👍3
👾 466 вопросов собесов на С# Developer
🔒 База реальных собесов
🔒 База тестовых заданий
👾 Список менторов
👩💻 С#
├ Вакансии
├ LeetCode ответы
└ Тесты
👩💻 Kotlin
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
👩💻 Swift
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
👣 Golang
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
👩💻 С/С++
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
👩💻 PHP
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
🖥 Frontend
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
🖥 Тестировщик
├ Вопросы собесов
├ Вакансии
└ Тесты
🖥 Python
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
👩💻 Java
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
🖥 Data Science
├ Вопросы собесов
├ Вакансии
└ Тесты
👩💻 DevOps
├ Вопросы собесов
├ Вакансии
└ Тесты
⚙ Backend
└ Вопросы собесов
👾 Список менторов
├ Вакансии
├ LeetCode ответы
└ Тесты
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
├ Вопросы собесов
├ Вакансии
└ Тесты
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
├ Вопросы собесов
├ Вакансии
├ LeetCode ответы
└ Тесты
├ Вопросы собесов
├ Вакансии
└ Тесты
├ Вопросы собесов
├ Вакансии
└ Тесты
└ Вопросы собесов
Please open Telegram to view this post
VIEW IN TELEGRAM
👍5❤2🔥1