Библиотека шарписта | C#, F#, .NET, ASP.NET – Telegram
Библиотека шарписта | C#, F#, .NET, ASP.NET
22.4K subscribers
2.5K photos
40 videos
85 files
4.74K links
Все самое полезное для C#-разработчика в одном канале.

По рекламе: @proglib_adv

Учиться у нас: https://proglib.io/w/b60af5a4

Для обратной связи: @proglibrary_feeedback_bot

РКН: https://gosuslugi.ru/snet/67a5c81cdc130259d5b7fead
Download Telegram
✏️ Запрет псевдо-вложенных модулей внутри типов в F# 10

В F# 10 добавили важное правило: теперь нельзя объявлять модуль внутри определения типа с тем же уровнем отступа, как сам тип.

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

Пример из старого кода:
type U =
| A
| B
module M = // на самом деле не вложенный модуль
let f () = ()


Правильный код:
type U =
| A
| B

module M =
let f () = ()


Это предотвращает частую ошибку, когда модуль кажется «вложенным» в тип, но на самом деле не является таковым.

🔸 Математика для Data Science
🔸 Получить консультацию менеджера
🔸 Сайт Академии 🔸 Сайт Proglib

🐸Библиотека шарписта

#sharp_view
Please open Telegram to view this post
VIEW IN TELEGRAM
👍4👾2🌚1
📘 4 декабря стартует набор на курс «Математика для разработки AI-моделей»

Если вы работаете с моделями или хотите перейти в DS/ML, декабрь — идеальный момент закрыть фундаментальные пробелы.

На курсе вы разберёте ключевые разделы, которые лежат в основе современных AI-моделей: линейная алгебра, анализ, оптимизация, математический анализ, вероятности, статистика. Всё через практику в Python.

В программе живые занятия с экспертами AI-индустрии (SberAI, ВШЭ, WB&Russ), разбор реальных задач, квизы и финальный проект.

🌐 Формат: онлайн + доступ к записям

🎁 Бонусы: курс «Школьная математика» в подарок, бесплатный тест по математике

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

👉 Записаться на курс
🥰2
📞 Комбинации букв телефонного номера: решение за один проход рекурсии

Задача — сгенерировать все возможные буквенные комбинации по цифрам телефона, где каждая цифра соответствует набору букв.

Идея решения: для каждой цифры берём соответствующие буквы и рекурсивно добавляем их к уже сформированным комбинациям.

Алгоритм:

1. Если входная строка пуста, возвращаем пустой результат

2. Используем массив с отображением цифр на наборы букв.

3. Рекурсивно проходим по цифрам, добавляя буквы к текущей комбинации

4. Когда достигнут конец строки, сохраняем сформированную комбинацию.

Решение:
public class Solution {
private static readonly string[] map = { "", "", "abc", "def", "ghi", "jkl", "mno", "pqrs", "tuv", "wxyz" };

public IList<string> LetterCombinations(string digits) {
var result = new List<string>();
if(string.IsNullOrEmpty(digits))
return result;
Backtrack(digits, 0, new StringBuilder(), result);
return result;
}

private void Backtrack(string digits, int index, StringBuilder current, List<string> result) {
if(index == digits.Length) {
result.Add(current.ToString());
return;
}

string letters = map[digits[index] - '0'];
foreach(char c in letters) {
current.Append(c);
Backtrack(digits, index + 1, current, result);
current.Length--;
}
}
}


🔸
ML для старта в Data Science
🔸 Получить консультацию менеджера
🔸 Сайт Академии 🔸 Сайт Proglib

🐸Библиотека шарписта

#dotnet_challenge
Please open Telegram to view this post
VIEW IN TELEGRAM
7🥰2
🔍 Устаревший синтаксис в F# 10

Раньше F# позволял опускать ключевое слово seq при создании последовательностей, что выглядело так:
{ 1..10 } |> List.ofSeq  // неявная последовательность


Это была особенность синтаксиса, но она расходилась с остальными вычислительными выражениями в языке и могла сбивать с толку.

Теперь компилятор рекомендует явно писать seq, чтобы сделать код однозначным и понятным:
seq { 1..10 } |> List.ofSeq


Сейчас это предупреждение, а не ошибка, чтобы дать время адаптироваться и исправить код. Но в будущих версиях F# это может превратиться в ошибку.

🔸 AI-агенты для DS-специалистов
🔸 Получить консультацию менеджера
🔸 Сайт Академии 🔸 Сайт Proglib

🐸 Библиотека шарписта

#sharp_view
Please open Telegram to view this post
VIEW IN TELEGRAM
🌲 Подборка вакансий для шарпистов

C#/.NET Developer на удалёнку

C#/.NET Developer с ЗП от 2 500 до 5 000$

C# / .NET Разработчик, middle, middle+ — от 190 000 до 290 000 ₽

🔸 AI-агенты для DS-специалистов
🔸 Получить консультацию менеджера
🔸 Сайт Академии 🔸 Сайт Proglib

➡️ Еще больше топовых вакансий — в нашем канале C# Jobs

🐸 Библиотека шарписта
Please open Telegram to view this post
VIEW IN TELEGRAM
🧑‍💻 Проекция колонок вместо сущностей в запросах

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

Пример проекции колонок с использованием LINQ:
var dto = await db.Users
.Where(u => u.Id == id)
.Select(u => new UserDto(u.Id, u.Name))
.SingleOrDefaultAsync(ct);


Здесь из таблицы пользователей выбираются только Id и Name, которые помещаются в объект UserDto.

🔹 ML для старта в Data Science
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#il_люминатор
Please open Telegram to view this post
VIEW IN TELEGRAM
🥰2
🛠 Строгая проверка назначения атрибутов в F# 10

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

Раньше F# позволял неявно применять атрибуты к неподходящим целям без предупреждений. Из-за этого возникали баги, например:

• Тестовые атрибуты не работали, если функция не имела (), и тесты не запускались

• Атрибуты-анализаторы иногда игнорировались, приводя к сбоям в CI без очевидной причины.

Пример такого кода, который никак не работал:
[<Fact>]
let ``this is not a function`` = // никак не запускался тест
Assert.True(false)


Теперь компилятор выдаёт предупреждение при неверном применении атрибутов:
[<Fact>]
//^^^^ предупреждение FS0842: атрибут нельзя применять к свойству, полю и т.п.
let ``works correctly`` =
Assert.True(true)


Атрибуты должны применяться только к совместимым элементам, например, к методам.

🔹 Алгоритмы и структуры данных
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#sharp_view
Please open Telegram to view this post
VIEW IN TELEGRAM
🥰2👍1🌚1
🛠 .NET MAUI и работа с возрастом

С началом 2026 года в США вступают в силу новые требования по верификации возраста пользователей для мобильных и десктопных приложений.

Да, это затрагивает несколько штатов в США, но стоит держать руку на пульсе.

.NET MAUI предоставляет удобный способ решения этой задачи с помощью единого интерфейса IAgeSignalService и трёх платформо-специфичных реализаций:

• Для Android используется Google Play Age Signals API, который возвращает пять статусов в зависимости от ситуации: от подтверждённого возраста до ожидания одобрения опекуна.

• На iOS применяется Apple Declared Age Range API, работающий на устройствах с iOS 26 и выше, отображающий возрастной диапазон и информацию о том, кто его подтвердил — сам пользователь или опекун.

• Windows предлагает Windows Age Consent API с упрощённой классификацией пользователей на три категории: ребёнок, несовершеннолетний и взрослый.

Главное преимущество — единая точка интеграции и адаптация под каждый API за счёт условной компиляции и инъекции зависимостей. Достаточно подключить сервис в MauiProgram, чтобы обеспечить проверку возраста на нужной платформе.

➡️ Блог Microsoft

🔹 AI-агенты для DS-специалистов
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#sharp_view
Please open Telegram to view this post
VIEW IN TELEGRAM
5👍1
Math for .NET Developers

Использовать ML.NET или Accord.net — это полдела. Чтобы кастомизировать модели и понимать, почему сеть не сходится, нужно лезть под капот. Там живут матрицы, производные и векторы.

Завтра стартуем курс «Математика для разработки AI-моделей».

🛠 Темы: Линал, матан, теорвер.

💸 Цена: 28 200 ₽ (новогодний прайс).

Дедлайн: Старт завтра.
Интегрируйте знания в свой стек:

🔗 Ссылка на курс

Debug your math:
@proglib_academy_webinar_bot
😁52
⚙️ Используйте AsNoTracking() для запросов только на чтение

Если нужно получить данные из базы без их изменения, лучше использовать AsNoTracking():
var posts = await db.Posts.AsNoTracking()
.Where(p => p.Published)
.ToListAsync(ct);


Метод AsNoTracking() говорит Entity Framework не отслеживать изменения для полученных объектов.

🔹 Практический интенсив «Архитектуры и шаблоны проектирования»
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#sharp_view
Please open Telegram to view this post
VIEW IN TELEGRAM
👍13🥱6
👨‍💻 Поддержка and! в task-вычислениях F# 10

В F# 10 библиотека FSharp.Core получила улучшение — поддержку оператора and! в вычислительном выражении task.

Раньше, чтобы ждать несколько задач параллельно, нужно было либо ждать их последовательно:
task {
let! a = fetchA()
let! b = fetchB()
return combineAB a b
}


Либо использовать Task.WhenAll для ожидания сразу всех:
task {
let ta = fetchA()
let tb = fetchB()
let! results = Task.WhenAll([| ta; tb |])
return combineAB ta.Result tb.Result
}


Первый вариант простой, но последовательный, второй — параллельный, но сложнее по синтаксису.

Теперь с оператором and! можно одновременно ждать несколько задач легко и понятно:
task {
let! a = fetchA()
and! b = fetchB()
return combineAB a b
}


Это сочетает простоту первого примера с параллельным исполнением из второго. Код становится компактным и выразительным.

🔹 Практический интенсив «Архитектуры и шаблоны проектирования»
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#sharp_view
Please open Telegram to view this post
VIEW IN TELEGRAM
🥰2
❗️ Microsoft признала масштабный баг в интерфейсе Windows 11 24H2 и 25H2

У части пользователей Windows 11 после установки последних обновлений в версиях 24H2 и 25H2 начали ломаться ключевые элементы интерфейса.

Проблема затрагивает базовые функции оболочки и выглядит как обычный «заглючивший» рабочий стол, но на деле связана с ошибками в самих системных компонентах.

Временное решение — установка актуальных патчей, использование опубликованных обходных скриптов или откат проблемных обновлений, если интерфейс стал нестабильным после апдейта.

➡️ Источник

🔹 Математика для разработки AI-моделей
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#async_news
Please open Telegram to view this post
VIEW IN TELEGRAM
👏93👍3🌚2👾1
🔑 Управление HttpClient по ключам

С .NET 9 можно управлять зависимостями по ключам. Буквально регистрировать и получать, к примеру, конфиги для HttpClient.

Как это работает

AddAsKeyed() — новый метод расширения для регистрации именованных HttpClient как Keyed Service в DI. Имя клиента становится ключом, по которому можно получать конкретный экземпляр.

• Внедрение осуществляется с помощью атрибута [FromKeyedServices("key")] или через Func<string, HttpClient> для динамического выбора клиента по ключу.

• В отличие от старых подходов с именованными или типизированными клиентами, внедрение зависимостей по ключам позволяет упростить код и уменьшить лишние вызовы фабрики IHttpClientFactory.

Пример регистрации и использования:
var builder = WebApplication.CreateBuilder(args);

// Регистрация HttpClient с ключом "github"
builder.Services.AddHttpClient("github", c =>
{
c.BaseAddress = new Uri("https://api.github.com/");
c.DefaultRequestHeaders.Add("Accept", "application/vnd.github.v3+json");
c.DefaultRequestHeaders.Add("User-Agent", "dotnet");
})
.AddAsKeyed();

var app = builder.Build();

// Внедрение HttpClient по ключу "github"
app.MapGet("/", ([FromKeyedServices("github")] HttpClient httpClient) =>
{
return httpClient.GetFromJsonAsync<Repo>("/repos/dotnet/runtime");
});

app.Run();

record Repo(string Name, string Url);


Преимущества Keyed DI

• Минимизирует необходимость вручную создавать и хранить экземпляры через IHttpClientFactory.

• Позволяет внедрять в сервисы и контроллеры правильно настроенные клиенты с простым указанием ключа.

• Улучшает читаемость и поддержку кода, особенно если в проекте много разных конфигураций HttpClient.

• Можно глобально включить ключевой DI для всех клиентов через ConfigureHttpClientDefaults.

Важные моменты

• По умолчанию AddAsKeyed() регистрирует HttpClient с областью видимости Scoped, но можно настроить и другой жизненный цикл.

• Нужно внимательно следить за временем жизни сервисов, чтобы избежать утечек памяти и проблем с соединениями.

• При ошибочном использовании ключа сервис выдаст стандартное исключение, помогая быстро находить и исправлять конфигурационные ошибки.

🔹 ML для старта в Data Science
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#il_люминатор
Please open Telegram to view this post
VIEW IN TELEGRAM
9🔥9👍3
🔄 Отмена запросов в EF

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

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

В Entity Framework для управления отменой используется CancellationToken. Его можно передавать в асинхронные методы, например:
await db.SaveChangesAsync(ct);


Переданный CancellationToken позволяет прервать выполнение метода, если операция была отменена.

🔹 Математика для Data Science
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#sharp_view
Please open Telegram to view this post
VIEW IN TELEGRAM
🥰4👍2
🧑‍💻 Честность в айти — это грех

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

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

💬 Как думаете лучше приврать или сказать как есть? Где ложь во благо, а где во вред? Делитесь в комментах своими размышлениями 👇

🔹 Практический интенсив «Архитектуры и шаблоны проектирования»
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#entry_point
Please open Telegram to view this post
VIEW IN TELEGRAM
👍21🥰1
C# мощный, но математика универсальна

ML.NET развивается, но фундамент Data Science остаётся неизменным. Чтобы эффективно работать с данными (даже в .NET-среде), нужно понимать линейную алгебру и статистику.

Мы добавили живые вебинары в наш курс по математике для AI.

Программа ближайших лекций:

Vectors & Matrices: операции, ранги, СЛАУ;
Linear Regression: реализация МНК, интерпретация весов;
SVD: матричные разложения и рекомендательные системы.
Практика на Python (NumPy), но алгоритмическая суть переносится на любой язык.

Регистрация закрывается 9 декабря:
https://clc.to/LojFzw
1😁1
✏️ Задача без подвоха

Дан массив длиной 2n в виде [x1,x2,xn,y1,y2,yn] нужно вернуть массив [x1,y1,x2,y2,xn,yn], то есть перемешать.

Идея решения

Логически делим массив на две половины по n элементов и в одном цикле по индексу i собираем ответ в новый массив result.
На каждой итерации кладем сначала элемент из первой половины nums[i] потом из второй nums[i+n].

Так мы проходим вход один раз время O(n), где n это половина массива.

Решение:
public class Solution
{
public int[] Shuffle(int[] nums, int n)
{
int[] result = new int[2 * n];
int index = 0;

for (int i = 0; i < n; i++)
{
result[index++] = nums[i];
result[index] = nums[i + n];
index++;
}

return result;
}
}


Ключевой момент в том что мы никогда не выходим за границы
первая половина идет по индексам от нуля до n минус один вторая от n до 2n минус один, а индекс в result просто сдвигается на два шага за итерацию.

➡️ Попробовать решить

🔹 Практический интенсив «Архитектуры и шаблоны проектирования»
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

🐸Библиотека шарписта

#dotnet_challenge
Please open Telegram to view this post
VIEW IN TELEGRAM
👍6🥱4🥰1👏1
Как правильно реализовать освобождение ресурсов в IAsyncDisposable?

Короткий ответ: Реализуйте шаблон с охраной от повторного вызова: DisposeAsync() вызывает приватный DisposeAsyncCore() и синхронный Dispose(false), закрывает IAsyncDisposable ресурсы через await using, остальные — в Dispose. Используйте AsyncLazy/флаг disposed, прокидывайте CancellationToken только там, где это безопасно, и учитывайте, что await using всегда вызывает именно DisposeAsync().

🔹 Курс «Программирование на языке Python»
🔹 Получить консультацию менеджера
🔹 Сайт Академии 🔹 Сайт Proglib

Библиотека собеса по С#
👾10