1.83K subscribers
3.3K photos
132 videos
15 files
3.58K links
Блог со звёздочкой.

Много репостов, немножко программирования.

Небольшое прикольное комьюнити: @decltype_chat_ptr_t
Автор: @insert_reference_here
Download Telegram
Forwarded from Varlamov News (Philipp Kireev)
Все же видели тот мем про волка, который боже как хорош и у которого так мощны лапищи? Конечно видели!

https://memepedia.ru/sherstyanoj-volchara-bozhe-kak-ya-xorosh/

Я сразу к делу ... короче ... оказалось, что это не волк, а волчица. Журнал National Geographic опубликовал историю снимка, фотограф Аарон Хью ради него наблюдал за этой стаей три дня.

https://www.instagram.com/p/B8VovLjHOfR/
Наконец-то можно Github автоматизировать
Тут Github выпустил бету официального консольного клиента.

Написан конечно же на go и поддерживает linux, Mac OS (есть в brew) и Windows.
Уже поддерживает создание пулл реквестов и issues, позже можно мониторить состояние github actions.

Страница проекта: https://cli.github.com/
Репозиторий: https://github.com/cli/cli
Статья в блоге Github: https://github.blog/2020-02-12-supercharge-your-command-line-experience-github-cli-is-now-in-beta/
#gamedev

Вы когда-нибудь хотели прогуляться по трёхмерному фракталу? Что ж, теперь вы можете.
Всё ещё в разработке, но выглядит потрясающе.

https://bananaft.itch.io/yedomaglobula
Блог*
Photo
Телеграм зашакалил фотку :/
В нормальном качестве можно посмотреть по ссылке
Forwarded from Fail Cascade
я кстати недавно видел вывеску SPA салон и подумал что это вебстудия
Нужно ли тестировать приватный функционал (предполагается, что у вас есть способ делать это без хаков и костылей)?
Anonymous Poll
66%
Да
20%
Нет
14%
Всё не так однозначно (в чат канала)
Блог*
Нужно ли тестировать приватный функционал (предполагается, что у вас есть способ делать это без хаков и костылей)?
Буду признателен, если вы поделитесь этим опросом. Я хочу узнать мнение людей помимо подписчиков каналов
Блог*
Нужно ли тестировать приватный функционал (предполагается, что у вас есть способ делать это без хаков и костылей)?
Забыл упомянуть: приватный функционал считается достаточно нетривиальным, чтобы его тестирование имело смысл. Ну, так, на всякий случай.
Если вы думаете, что я обленился и забыл про блог, то вы совершенно правы вот вам тизер завтрашней статьи:
#meme #моё #prog #rust

You vs the guy she told you not to worry about
#моё #prog #rust

В крейте time есть структура Date с методом format, который возвращает String со датой, отформатированной согласно переданному формату. Выглядит это примерно так (пример из документации):

assert_eq!(date!(2019-01-02).format("%Y-%m-%d"), "2019-01-02");

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

Как примерно должен выглядеть код? Нам нужно абстрагироваться от конкретных типов по операции "отформатируй сюда дату", чтобы из элементарных форматировщиков можно было собрать составной. В самой операции нам, очевидно, требуются: сам форматировщик, дата и буфер, куда будут записываться данные. Мы не хотим возвращать строку непосредственно, потому что это при объединении привело бы ко множеству ненужных мелких аллокаций. Также мы не хотим, чтобы форматировщики могли удалять из буфера данные, поэтому мы сделаем обёртку над строкой с более узким интерфейсом:

use std::fmt;

#[derive(Default)]
pub struct Buf {
inner: String,
}

impl Buf {
pub fn new() -> Self {
Self::default()
}

pub fn append(&mut self, s: &str) {
self.inner += s;
}

// Этот метод позволит нам использовать макрос `write!` на `Buf`.
// Он позволяет не безусловно выделять новую строку,
// а использовать место в уже имеющейся
pub fn write_fmt(&mut self, args: fmt::Arguments) -> fmt::Result {
self.inner.write_fmt(args)
}
}

Сам общий интерфейс форматировщиков:

use std::fmt;
use time::Date;

pub trait FormatDate {
fn format_date(&self, b: &mut Buf, d: Date) -> fmt::Result;
}

(проблем с тем, чтобы принимать Date по значению, нет, потому что это Copy-тип).

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

impl FormatDate for &'_ str {
fn format_date(&self, b: &mut Buf, _: Date) -> fmt::Result {
b.append(self);
Ok(())
}
}

Теперь напишем реализацию для, скажем, дня даты:

pub struct DayOf;

impl FormatDate for DayOf {
fn format_date(&self, b: &mut Buf, d: Date) -> fmt::Result {
write!(b, "{:02}", d.day())
}
}

Формат "{:02}" означает, что для печати дня отведено два места, и если в номере дня всего одна цифра, то вывод будет дополнен слева нулями. Форматировщики для номера месяца и года пишутся аналогично, поэтому не будем подробнее на этом останавливаться.
Как же теперь объединить всё это? Написать реализацию для кортежей форматировщиков, разумеется! Так как вариадических обобщённых типов в Rust нет, а руками писать реализации мне лень, напишем макрос:

macro_rules! impl_for_tuples {
() => {};
($head:ident $(, $rest:ident)*) => {
impl<$head, $($rest),*> FormatDate for ($head, $($rest,)*)
where
$head: FormatDate,
$($rest: FormatDate,)*
{
fn format_date(&self, b: &mut Buf, date: Date) -> fmt::Result {
#[allow(non_snake_case)]
let &(ref $head, $(ref $rest,)*) = self;
$head.format_date(b, date)?;
$($rest.format_date(b, date)?;)*
Ok(())
}
}
impl_for_tuples!($($rest),*);
};
}

impl_for_tuples!(A, B, C, D, E, F, G, H);

Добавим для удобства extension trait:

pub trait DateExt {
fn format_into<F: FormatDate>(self, b: &mut Buf, f: F) -> fmt::Result;
fn format_as<F: FormatDate>(self, f: F) -> String;
}

impl DateExt for Date {
fn format_into<F: FormatDate>(self, b: &mut Buf, f: F) -> fmt::Result {
f.format_date(b, self)
}
fn format_as<F: FormatDate>(self, f: F) -> String {
let mut buf = Buf::default();
let _ = self.format_into(&mut buf, f);
buf.inner
}
}

И проверим, как работает:

use time::date;

// Очень удобный макрос
let d = date!(2020-02-18);
let format = (DayOf, "/", MonthOf, "/", YearOf);
// Обратите внимание на ноль впереди в месяце
assert_eq!(d.format_as(format), "18/02/2020");

Работает!