LINUX.ORG.RU

То что сложно реализовать на других языках

 


0

3

Разбираюсь с библиотекой qsp и решил с вами поделится кусочком кода, а точнее реализация crc32. Автор кода, решил создать свой собственный crc32, на базе CRC-32/ISO-HDLC, взяв от туда таблицу, но изменил стартовое значение, и еще по мелочи:

int qspCRC(void *data, int len)
{
    unsigned char *ptr;
    int crc = 0;
    ptr = (unsigned char *)data;
    while (len--)
        crc = (qspCRCTable[(crc & 0xFF) ^ *ptr++] ^ crc >> 8) ^ 0xD202EF8D;
    return crc;
}

В чем прелесть: Использует int, но фактически работает как unsigned int. Вся логика на переполнение - и это как то работает, хотя вроде это UB. Автор кода крут (без шуток), я не спорю, но переписать это на любой другой язык, который будет контролировать переполнение - будет крайне сложно. Почему автор не использовал любой из стандартных алгоритмов crc, как он использовал библиотеку для regexp - загадка.

★★★★
Ответ на: комментарий от numas13

Кстати, в реально мощном языке никакие макросы не нужны, вот что скоро С++ бояре будут писать вместо твоих портянок и кривых string_contains: https://godbolt.org/z/jb9vb99fc

alysnix, в примере как раз рефлексия, ты интересовался зачем она нужна, вот еще один пример набрался.

MOPKOBKA ★★★★★
()
Последнее исправление: MOPKOBKA (всего исправлений: 1)
Ответ на: комментарий от numas13

X Macro я уже написал, смотри выше. Он кстати тоже может enum обрабатывать. По моему очень забавно. Но видимо ты ждешь реализации трейта на сишке, не знаю что тебя не устраивает.

MOPKOBKA ★★★★★
()
Последнее исправление: MOPKOBKA (всего исправлений: 2)
Ответ на: комментарий от alysnix

ну раз у вас есть сумма типов, то определите и операцию разности. Для пущей полноты своей мегаалгебры, чего стесняться?

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

anonymous
()
Ответ на: комментарий от anonymous

строчки не «складывают», а конкатенируют, гражданин.

и обратная операция для конкатенации - отрубание хвоста из указанной строки. типа remove_last(«bla-bla»).

самому алгебраисту догадаться сложно ведь?

alysnix ★★★
()
Последнее исправление: alysnix (всего исправлений: 2)
Ответ на: комментарий от MOPKOBKA

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

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

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

alysnix ★★★
()

Использует int, но фактически работает как unsigned int.

И при этом дейстивтельно получается CRC — обнаружение и коррекция ошибок?

изменил стартовое значение

В смысле порождающий полином? И не снизил расстояние Хэмминга? Или это всё код от балды?

mky ★★★★★
()
Ответ на: комментарий от anonymous

Тебе же выше кто-то другой уже объяснил про слово «алгебра». Ты, вообще, читаешь, что тебе пишут?

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

конструкт, который он там породил с двумя некоммутативными операциями типа сложения и умножения строго говоря это не теория множеств. такая алгебра называется некоммутативным кольцом(ищи в энторнетах - «некоммутативное кольцо») с некоммутативным сложением, и является некоей абракадаброй.

а его хваленая тип-сумма опирается на похоже неверное определение операции сложения.

операция сложения обычно полагается коммутивной, иначе это не сложение, а что-то другое. вот например конкатенация, на которую напоролся некий аноним со строками. конкатенация это НЕ СЛОЖЕНИЕ! хоть и вам нарисовали плюсик, для синтаксического сахара.

alysnix ★★★
()
Ответ на: комментарий от alysnix

строчки не «складывают», а конкатенируют, гражданин.

Конкатенация обладает моноидальными свойствами, поэтому для «сложения над строками» вполне пойдёт.

и обратная операция для конкатенации - отрубание хвоста из указанной строки. типа remove_last(«bla-bla»).

Но эта операция не эквивалентна вычетанию для строк. Как минимум, потому что не будет работать для случае a + b - a. В общем, строки – отличный пример сложения без вычетания.

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

А вот чего в C++ нет относительно Rust, так это нормального паттерн-матчинга.

anonymous
()
Ответ на: комментарий от anonymous

Конкатенация обладает моноидальными свойствами, поэтому для «сложения над строками» вполне пойдёт.

не мудрите, у вас - «сложение над строками» некоммутативно. это конкатенация, которая некоммутативна по природе своей.

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

alysnix ★★★
()
Ответ на: комментарий от alysnix

операция сложения обычно полагается коммутивной, иначе это не сложение, а что-то другое

Тебя обманули. Сложение не обязано быть коммутативным. Как пример, сложение ординалов: 1+w!=w+1.

Ты реально застрял в 10 классе, раз считаешь, что алгебра может быть только над числами. Алгебру можно сделать над любыми множествами, алгебраическая топология тому примером.

anonymous
()
Ответ на: комментарий от mky

И при этом дейстивтельно получается CRC — обнаружение и коррекция ошибок?

На базе этого, движок проверяет файл игр и сейвы.

В смысле порождающий полином? И не снизил расстояние Хэмминга? Или это всё код от балды?

Да. не знаю. Автор кода посчитал, что так лучше (зачем не понятно). Может реализация стандартного crc требует каких то авторских, ограничение по лицензии - я не знаю!?

Silerus ★★★★
() автор топика
Последнее исправление: Silerus (всего исправлений: 1)
Ответ на: комментарий от anonymous

Ты реально застрял в 10 классе, раз считаешь, что алгебра может быть только над числами

над какими еще числами??? мы давно говорим о множествах и даже последовательностях в виде строк.

для тебя конкатенация тоже «сложение»?

alysnix ★★★
()
Ответ на: комментарий от alysnix

для тебя конкатенация тоже «сложение»?

Для сложения обычно достаточно моноидальных свойств: ассоциативного оператора и нулевого элемента. Конкатенация этому удовлетворяет.

С другой стороны

мы давно говорим о множествах

Для типов сложение вполне себе коммутативно.

enum T {
  A(int),
  B(char)
}

От перестановки строчек тут не поменяется вообще ничего.

anonymous
()
Ответ на: комментарий от Silerus

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

в данном случае интов там быть не должно, ибо хеши всегда положительны(и даже не ноль), и есть отображение на множество натуральных.

alysnix ★★★
()
Ответ на: комментарий от anonymous

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

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

псевдокод, записываем int в «тип сумму».

(int, float) <- int
(float, int) <- int

в первом случае тег варианта = 0, во втором = 1.

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

итак что отвечает раст(или кто-то там) на вопрос - являются ли эти типы эквивалентными, то есть приводимыми по умолчанию. для меня вот очевидно, что подставить значение первого типа во второй - это систему сломать. у них разные теги внутри

alysnix ★★★
()
Последнее исправление: alysnix (всего исправлений: 1)
Ответ на: комментарий от Silerus

На базе этого, движок проверяет файл игр и сейвы.

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

зачем не понятно

В этом мире полно кода, написанного непонятно из каких причин, но написано, как-то работает, трогать не будем. Тем более, поменять алогоритм расчёта контрольной суммы не так просто, если уже куча файлов со старой суммой.

mky ★★★★★
()
Ответ на: комментарий от alysnix

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

Ичо? Это разные типы, хоть и изоморфные, ясен хер не надо их значения напрямую сравнивать.

anonymous
()
Ответ на: комментарий от alysnix

В раст enum это уникальный тип. Его можно использовать как стандартный с/с++ enum,если нахлабучить сверху макросы PatrialEq Eq. Его можно использовать как variant или any (так он чаще всего наверное и используется). Например

enum SomeThing{
    Str(String),
    Num(u32),
    Bool(bool)
}

И тогда данные надо вытаскивать одним из способов

let a = SomeThing::Str("hello world".to_string);
if let SomeThing::Str(val) = a{
 println!("{val}");
}
match a{
 SomeThing::Str(val)=>...,
 SomeThing::Num(val)=>...,
 _=> ...
}

Если я правильно понял, что вы спрашиваете

Silerus ★★★★
() автор топика
Последнее исправление: Silerus (всего исправлений: 1)
Ответ на: комментарий от anonymous

Это разные типы, хоть и изоморфные, ясен хер не надо их значения напрямую сравнивать.

конкретный вопрос в следующем, опять псевдокод:

type T1 = int | float;
type T2 = float | int;

var x:T1 = 100;
var xx: T2 = x; ///присваивание корректно?

если некорректно - сумма типов некоммутативна.

alysnix ★★★
()
Ответ на: комментарий от alysnix

если некорректно - сумма типов некоммутативна.

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

Ты какой-то тупой, ей богу.

anonymous
()
Ответ на: комментарий от anonymous

тупой тут ты. в канпиляторах(языках) есть понятие структурной эквивалентностью типов, але. например, во всю ширь она работает в случае массивов например, где int[10] и int[10] это один тип или функциональны типах или еще где. указатель *T и другой указатель *T - это тоже структурно эквивалентные типы, пусть даже обьявлены в разных местах…впрочем тебя учить, только портить.

и «утиная типизация» - некое расширительное толкование структурной эквивалентости.

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

вопрос тут такой - сумма на типах коммутативна или нет. если да это автоматом породит структурную эквивалентость. и причем тут этот ваш раст?

давай тогда так спросим

var x: int | float = 100;
var x1: int | float = x; ///присваивание корректно?
var x2: float | int = x; ///присваивание корректно?

alysnix ★★★
()
Последнее исправление: alysnix (всего исправлений: 2)
Ответ на: комментарий от alysnix

в канпиляторах(языках) есть понятие структурной эквивалентностью типов

В некоторых есть, в некоторых нет. Какое отношение это имеет к изоморфности типов?

Классический пример: int и wchar_t структурно эквивалентны, но не изоморфны, потому как не каждый int будет валидным wchar_t.

anonymous
()
Ответ на: комментарий от anonymous

Какое отношение это имеет к изоморфности типов?

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

alysnix ★★★
()
Ответ на: комментарий от anonymous

В некоторых есть, в некоторых нет.

во всех это есть, ну может кроме брейнфака. потому что иначе код будет писать немамона. и такие переменные будут несовместимы например.

a: int[100];
b: int[100];

и еще много чего несовместимого там окажется.

alysnix ★★★
()
Ответ на: комментарий от alysnix

Какой же ты смешной!

Обращаюсь ко всем остальным. Вполне хорошая стратегия: разобраться и в C++, и в Rust. Можно использовать оба языка одновременно. Можно использовать один из них. Можно их, вообще, оба избегать. Выбор за вами!

Желаю только не страдать узостью и однобокостью мышления. Все-таки старайтесь воспринимать мир таким, какой он есть. И воспринимать языки программирования такими, какие они есть. А то смешно иногда получается со стороны.

Удачи в освоении и C++, и Rust! Оба языка стоят того, чтобы вы их попробовали


подпись: один из анонимусов, который был первым

anonymous
()
Ответ на: комментарий от anonymous

в мире известны порядка 9 тыс. языков программирования. почему из них нужно обратить внимание на с++ довольно понятно. но почему нужно еще учить и раст, для акробатических упражнений в свободное время, - непонятно.

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

а языков для полезного изучения полно. это и жава и шарп и голанг, и даже питон, scheme, луа, свифт и так далее. и в отличие от раста у них меньше «степень удивления» при взгляде на код.

вот как раз узость и однобокость - выбрать пару с++/раст и носится с ней, как ошпаренный.

alysnix ★★★
()
Последнее исправление: alysnix (всего исправлений: 1)
Ответ на: комментарий от alysnix

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

Операция суммы типов коммутативна, потому что для типов A + B и B + A можно определить функции ’f : A + B -> B + Aиg : B + A -> A + B, образующих изоморфизм между этими двумя типами. Другими словами, типыA + BиB + A` изоморфны друг другу.

тут нет вопроса про «изоморфизьм».

Ты просто не шаришь в терминологии, чувак. Да и вообще ни в чём не шаришь. Но мне нравится тебя поучать. Не потому что я верю, что ты способен к излечению, нет. А потому что кто-то другой может прочитать этот тред, увидеть твой дебилизм и научиться чему-то новому.

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

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

anonymous
()
Ответ на: комментарий от anonymous

Операция суммы типов коммутативна, потому что для типов A + B и B + A можно определить функции ’f : A + B -> B + Aиg : B + A -> A + B, образующих изоморфизм между этими двумя типами. Другими словами, типыA + BиB + A` изоморфны друг другу.

Вот жеж срань! Форматирование поехало :( Правильно вот так:

Операция суммы типов коммутативна, потому что для типов A + B и B + A можно определить функции f : A + B -> B + A и g : B + A -> A + B, образующих изоморфизм между этими двумя типами. Другими словами, типы A + B и B + A изоморфны друг другу.

anonymous
()
Ответ на: комментарий от anonymous

Ты просто не шаришь в терминологии, чувак. Да и вообще ни в чём не шаришь. … Не потому что я верю, что ты способен к излечению, нет.

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

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

Разве что.

anonymous
()
Ответ на: комментарий от anonymous

я бесконечно рад, что у тебя какие-то «типы» «суммы» и «изоморфизьм».

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

и значение этого тега зависит от порядка операндов в записи твоей суммы. то есть операция «суммы» эта некоммутативна!!!, поскольку в бинарном представлении есть зависимость от порядка операндов. или по твоему в типе-сумме селекция по типу значения делается святым духом?

я про тег говорю, а не про твои пустые абстрации с изоморфизьмом:)

alysnix ★★★
()
Ответ на: комментарий от anonymous

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

а у вас есть существо? вы бесплотный анонимный дух, а отвечать не пойми кому - все равно что разговаривать с телевизором.

почему вообще анонимов в топики пускают?

alysnix ★★★
()
Ответ на: комментарий от alysnix

QED.

А вообще смешно. Аноним с никнеймом сетует о том, что незарегистрированных анонимов пускают.

На аватарке — это ведь твоя подлинная паспортная фотография? И alysnix - это твоё настоящее, данное при рождении имя?

anonymous
()
Ответ на: комментарий от anonymous

твой тип-сумма в которым ты запутался, в реальном ЯП выглядит так

{
  tag:number
  union (A,B)
}

упрощаем, пусть A = true(T), B = false(F)

тогда для T + F имеем множество значений {(0,T), (1,F)}

тогда для F + T имеем множество значений {(1,T), (0,F)}

где твой изоморфизьм? это вообще разные множества. наличие селектора развалило твой изоморфизм.

alysnix ★★★
()
Последнее исправление: alysnix (всего исправлений: 1)
Ответ на: комментарий от alysnix

теперь тебе осталось спуститься с горшка на землю, и рассказать как «тип-сумма» устроен в бинарном виде в конкретном ЯП.

Зачем это делать? Это деталь реализации, причём достаточно незначительная. Не понимаю, почему у тебя так жопу от этого щекочет.

и ты вдруг увидишь, что там есть тег, что портит всю твою изоморфную картину.

Или нет. Те же GHC (Haskell) и Rustc умеют выкидывать этот тег, если при сборке можно доказать, что других кейсов в этом месте тупо не будет.

и значение этого тега зависит от порядка операндов в записи твоей суммы. то есть операция «суммы» эта некоммутативна!!!,

Не, не зависит. Серьёзно, вообще не зависит. В том же Haskell этот тег зависит от имени конструктора (читай, имени кейса), а на порядок тут посрать.

я про тег говорю, а не про твои пустые абстрации с изоморфизьмом:)

Зачем ты про тег тут пишешь? Задумайся об этом хоть на секунду.

anonymous
()
Ответ на: комментарий от anonymous

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

Несколько страниц? Я его тут уже несколько лет наблюдаю!

anonymous
()
Ответ на: комментарий от anonymous

В том же Haskell этот тег зависит от имени конструктора (читай, имени кейса), а на порядок тут посрать.

к хаскелю претензий пока нет. если оно так - то это правильно. вопрос - как это реализовано на нижнем уровне, с учетом эффективности.

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

alysnix ★★★
()
Ответ на: комментарий от anonymous

Я его тут уже несколько лет наблюдаю!

вместо того, чтобы благодарить за несколько лет увлекательного чтения, и скрашенное одиночество, ты, бесчестный аноним, на меня телеги модераторам пишешь небось!

смотри, боженька тебя накажет.

alysnix ★★★
()
Ответ на: комментарий от alysnix

вместо того, чтобы благодарить за несколько лет увлекательного чтения, и скрашенное одиночество, ты, бесчестный аноним, на меня телеги модераторам пишешь небось!

Модераторам я ничего не пишу. Они меня сами в приступах белой горячки банят. Зачем я им что-то писать буду?

// hateyoufeel

anonymous
()
Ответ на: комментарий от alysnix

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

Коммутативность сложения типов не имеет ровно ни малейшего отношения к тому, как эти суммы кодируются в памяти. Важно только то, что у условных int + char и char + int будет одно и то же множество значений в итоге. Разупорись уже и хотя бы википедию почитай.

anonymous
()
Ответ на: комментарий от alysnix

Ну, вот, ты же сам здесь построил изоморфизм: tag’ = 1 - tag.

Какая воинствующая безграмотность, которая прикрывается солидностью используемого инструмента, то есть прикрывается C++.


Первый анонимус

Я тут когда-то сам самоудалился. В годах 2019-2020 тут такой зашкаливающий нацпол был, что противно было находиться здесь. Интересно, а после самоудаления восстановить аккаунт могут? Пароль помню

anonymous
()
Ответ на: комментарий от anonymous

Какая воинствующая безграмотность, которая прикрывается солидностью используемого инструмента, то есть прикрывается C++.

В C++ нет ничего солидного. C и C++ – сраный позор всей индустрии.

anonymous
()
Ответ на: комментарий от anonymous

На C и C++ пишут большие системы - тот же линукс взять к примеру. Не потому, что язык хорош. Он, так - на «3» или «4». Просто технологические и политические риски одни из самых низких. Почти ни от кого не зависишь. Тот же Qt есть для десктопа. А так, язык, конечно, не фонтан.

Уже поэтому C и C++ имеют право на существование

anonymous
()