Секреты невозможных вычислений на GPU

    Наш опыт использования вычислительного кластера из 480 GPU AMD RX 480 при решении математических задач. В качестве задачи мы взяли доказательство теоремы из статьи профессора Чуднова А.М. “Циклические разложения множеств, разделяющие орграфы и циклические классы игр с гарантированным выигрышем“. Задача заключается в поиске минимального числа участников одной коалиции в коалиционных играх Ним-типа, гарантирующее выигрыш одной из сторон.



    Развитие CPU


    Первый процессор, получивший действительно массовое распространение – это 8086 от компании Intel, разработанный в 1978 году. Тактовая частота работы 8086 составляла всего 8 МГц. Спустя несколько лет появились первые процессоры внутри которых было 2, 4 и даже 8 ядер. Каждое ядро позволяло выполнять свой код независимо от других. Для сравнения — современный процессор Intel Core i9-7980XE работает на частоте 2,6 ГГц и содержит 18 ядер. Как видите — прогресс не стоит на месте!

    Развитие GPU


    Одновременно с развитием центральных процессоров развивались и видеокарты. В основном их характеристики важны для компьютерных игр, там новые технологии проявляются особенно красочно и рендеринг 3D картинки постепенно приближается к фотографическому качеству. В начале развития компьютерных игр расчет картинки выполнялся на CPU, но вскоре был достигнут предел изобретательности разработчиков 3D-графики, ухитрявшихся оптимизировать даже очевидные вещи (хороший пример тому — InvSqrt()). Так, в видеокартах стали появляться сопроцессоры со специальным набором команд для выполнения 3D вычислений. Со временем число таких команд росло, что, с одной стороны, позволяло гибче и эффективнее работать с изображением, а с другой — усложнило процесс разработки.

    С 1996 года начали выпускаться графические ускорители S3 ViRGE, 3dfx Voodoo, Diamond Monster и другие. В 1999 году nVidia выпустила процессор GeForce 256, введя в обиход термин GPU — графический процессор. Он уже универсальный, может заниматься геометрическими расчетами, преобразованием координат, расстановкой точек освещения и работой с полигонами. Отличие GPU от других графических чипов заключалось в том, что внутри, кроме специализированных команд, был набор стандартных команд, с помощью которых можно было реализовать свой алгоритм рендеринга. Это дало значительное преимущество, так как позволило добавлять любые спецэффекты, а не только те, которые уже запрограммированы в видеокарту. Начиная с GeForce 8000/9000 в GPU появились потоковые процессоры — уже полноценные вычислители. Их число варьировалось в зависимости от модели от 16 до 128. В современной терминологии они называются унифицированные шейдерные блоки, или просто шейдерные блоки. В производимых сегодня GPU AMD Vega 64 содержится 4096 шейдерных блока, а тактовая частота может достигать 1536 МГц!

    Что содержит в себе GPU


    Архитектура GPU отличается от CPU большим количеством ядер и минималистичным набором команд, направленных в основном на векторные вычисления. На уровне архитектуры решены вопросы параллельной работы большого числа ядер и одновременного доступа к памяти. Современные GPU содержат от 2-х до 4-х тысяч шейдерных блоков, которые объединены в вычислительные юниты (Compute Unit). При параллельных вычислениях особенно остро стоит проблема одновременного доступа к памяти. Если каждый из потоковых процессоров попытается выполнить запись в ячейку памяти то эти команду упрутся в блокировку и их необходимо будет поставить в очередь, что сильно снизит производительность. Поэтому потоковые процессоры выполняют команды небольшими группами: пока одна группа производит вычисления, другая загружает регистры и т.д. Также можно объединить ядра в рабочие группы, обладающие общей памятью и внутренними механизмами синхронизации.

    Еще одной важной особенностью GPU является наличие векторных регистров и векторных АЛУ, которые могут выполнять операции одновременно для нескольких компонентов вектора. Это в первую очередь нужно для 3D графики, но поскольку наш мир трехмерный, ничто не мешает использовать это для многих физических вычислений. При наличии свободных векторных АЛУ их можно использовать и для вычисления скалярных величин.

    Они такие разные, CPU и GPU


    Для полноценной работы вычислительной системы важны оба типа устройств. К примеру, мы выполняем пошаговую программу, некий последовательный алгоритм. Там нет возможности выполнить пятый шаг алгоритма, так данные для него рассчитываются на шаге четыре. В таком случае эффективнее использовать CPU с большим кэшем и высокой тактовой частотой. Но есть целые классы задач, хорошо поддающихся распараллеливанию. В таком случае эффективность GPU очевидна. Самый частый пример — вычисление пикселей отрендеренного изображения. Процедура для каждого пикселя почти одинаковая, данные о 3D объектах и текстурах находятся в ОЗУ видеокарты и каждый потоковый процессор может независимо от других посчитать свою часть изображения.

    Вот пример современной задачи — обучение нейронной сети. Большое количество одинаковых нейронов необходимо обучить, то есть поменять весовые коэффициенты каждого нейрона. После таких изменений нужно пропустить через нейросеть тестовые последовательности для обучения и получить вектора ошибок. Такие вычисления хорошо подходят для GPU. Каждый потоковый процессор может вести себя как нейрон и при вычислении не придется выстраивать решение последовательным образом, все наши вычисления будут происходить одновременно. Другой пример — расчет аэродинамических потоков. Необходимо выяснить возможное поведение проектируемого моста под воздействием ветра, смоделировать его аэродинамическую устойчивость, найти оптимальные места установки обтекателей для корректировки воздушных потоков или рассчитать устойчивость к ветровому резонансу. Помните знаменитый “танцующий мост” в Волгограде? Думаю, что никто не хотел бы оказаться в тот момент на мосту…

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

    GPU в руках программистов


    Для выполнения вычислений на GPU используется специальный язык и компилятор. Существует несколько фреймворков для выполнения общих вычислений на GPU: OpenCL, CUDA, С++AMP, OpenACC. Широкое распространение получили первые два, но использование CUDA ограничено только GPU от компании nVidia.

    OpenCL был выпущен в 2009 году компанией Apple. Позднее корпорации Intel, IBM, AMD, Google и nVidia присоединились к консорциуму Khronos Group и заявили о поддержке общего стандарта. С тех пор новая версия стандарта появляется каждые полтора-два года и каждый привносит все более серьезные улучшения.

    На сегодняшний день язык OpenCL C++ версии 2.2 соответствует стандарту C++14, поддерживает одновременное выполнение нескольких программ внутри устройства, взаимодействие между ними через внутренние очереди и конвейеры, позволяет гибко управлять буферами и виртуальной памятью.

    Реальные задачи


    Интересная задача из теории игр, в решении которой мы принимали участие — доказательство теоремы из статьи профессора Чуднова А.М. “Циклические разложения множеств, разделяющие орграфы и циклические классы игр с гарантированным выигрышем“. Задача заключается в поиске минимального числа участников одной коалиции в коалиционных играх Ним-типа, гарантирующее выигрыш одной из сторон.

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

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

    Сложность решения этой задачи в переборе огромного числа вариантов. Например, если мы ищем решение для n=25, то это 25 бит, а если n=100, то это уже 100 бит. Если взять количество всех возможных комбинаций, то для n=25 это 2^25=33 554 432, а для n=100 это уже 2^100=1 267 650 600 228 229 401 496 703 205 376 комбинаций. Возрастание сложности просто колоссальное!

    Такая задача хорошо распараллеливается, а значит она идеально подходит для нашего GPU кластера.

    Программисты vs математики


    Изначально математики решали эту задачу на Visual Basic в Excel, так удалось получить первичные решения, но невысокая производительность скриптовых языков не позволила продвинуться далеко вперед. Решение до n=80 заняло полтора месяца… Склоняем голову перед этими терпеливыми людьми.

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

    Следующим этапом оптимизации стало профилирование. Замер времени выполнения различных участков кода показал, что в некоторых ветках алгоритма сильно возрастала нагрузка на память, а также выявилось излишнее ветвление программы. Из-за этого “маленького” недочёта почти треть мощности CPU была не задействована.

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

    Вот и наступил этап подготовки программы для решения на GPU и код был модифицирован для работы в несколько потоков. Управляющая программа теперь занималась диспетчеризацией задач между потоками. В многопоточной среде скорость вычисления увеличилась в 5 раз! Этого удалось добиться за счет одновременной работы 4 потоков и объединения функций.

    На этом этапе решение производило верные расчеты до n=80 за 10 минут, тогда как в Exсel’e эти расчеты занимали полтора месяца! Маленькая победа!

    GPU и OpenCL


    Было принято решение использовать OpenCL версии 1.2, чтобы обеспечить максимальную совместимость между различными платформами. Первичная отладка производилась на CPU от Intel, потом на GPU от Intel. Уже потом перешли на GPU от AMD.

    В версии стандарта OpenCL 1.2 поддерживаются целочисленные переменные размерностью 64 бита. Размерность в 128 бит ограничено поддерживается AMD, но компилируется в два 64-х битных числа. Из соображений совместимости и для оптимизации производительности было решено представлять число размерностью 256 бит как группу 32-х битных чисел, логические побитовые операции над которыми производятся на внутреннем АЛУ GPU максимально быстро.
    Программа на OpenCL содержит ядро — функцию, которая является точкой входа программы. Данные для обработки загружаются с CPU в ОЗУ видеокарты и передаются в ядро в виде буферов — указателей на массив входных и выходных данных. Почему массив? Мы же выполняем высокопроизводительные вычисления, нам нужно много задач, выполняемых одновременно. Ядро запускается на устройстве во множестве экземпляров. Каждое ядро знает свой идентификатор и берет именно свой кусочек входных данных из общего буфера. Тот случай, когда самое простое решение — самое эффективное. OpenCL — это не только язык, но и всеобъемлющий фреймворк, в котором досконально продуманы все мелочи научных и игровых вычислений. Это здорово облегчает жизнь разработчику. Например, можно запустить много потоков, диспетчер задач разместит их на устройстве сам. Те задачи, которые не встали на немедленное исполнение, будут поставлены в очередь ожидания и запущены по мере освобождения вычислительных блоков. У каждого экземпляра ядра есть свое пространство в выходном буфере, куда он и помещает ответ по завершению работы.

    Основная задача диспетчера OpenCL — обеспечить параллельное выполнение нескольких экземпляров ядра. Здесь применён накопленный десятилетиями научный и практический опыт. Пока часть ядер загружает данные в регистры, другая часть в это время работает с памятью или выполняет вычисления — в результате ядро GPU всегда полностью загружено.
    Компилятор OpenCL хорошо справляется с оптимизацией, но разработчику влиять на быстродействие проще. Оптимизация под GPU идет в двух направлениях — ускорение выполнения кода и возможность его распараллеливания. Насколько хорошо распараллеливается код компилятором зависит от нескольких вещей: количество занимаемых scratch регистров (которые располагаются в самой медленной памяти GPU — глобальной), размер скомпилированного кода (надо поместиться в 32 кб кэша), количество используемых векторных и скалярных регистров.

    ComBox A-480 GPU или один миллион ядер


    Эта самая интересная часть проекта, когда от Excel мы перешли на вычислительный кластер состоящий из 480 видеокарт AMD RX 480. Большого, быстрого, эффективного. Полностью готового к выполнению поставленной задачи и получению тех результатов, которых мир еще никогда не видел.

    Хочется отметить что на всех этапах совершенствования и оптимизации кода мы запускали поиск решения с самого начала и сравнивали ответы новой версии с предыдущими. Это позволяло быть уверенными, что оптимизация кода и доработки не вносят ошибки в решения. Тут нужно понимать, что правильных ответов в конце учебника нет, и никто в мире их не знает.
    Запуск на кластере подтвердил наши предположения по скорости решений: поиск последовательностей для n>100 занимал около часа. Было удивительно видеть как на кластере ComBox A-480 новые решения находились за минуты, в то время как на CPU это занимало многие часы.

    Всего через два часа работы вычислительного кластера мы получили все решения до n=127. Проверка решений показала, что полученные ответы достоверны и соответствуют изложенным в статье теоремам профессора Чуднова А.М.

    Эволюция скорости


    Если посмотреть прирост производительности в ходе решения задачи, то результаты были примерно такими:

    • полтора месяца до n=80 в Excel;
    • час до n=80 на Core i5 с оптимизированной программой на С++;
    • 10 минут до n=80 на Core i5 с использованием многопоточности;
    • 10 минут до n=100 на одном GPU AMD RX 480;
    • 120 минут до n=127 на ComBox A-480.

    Перспективы и будущее


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

    Возможные области применения параллельных вычислений:

    • задачи автоматического управления транспортными средствами и дронами;
    • расчеты аэродинамических и гидродинамических характеристик;
    • распознавание речи и визуальных образов;
    • обучение нейронных сетей;
    • задачи астрономии и космонавтики;
    • статистический и корреляционный анализ данных;
    • фолдинг белок-белковых соединений;
    • ранняя диагностика заболеваний с применением ИИ.

    Отдельное направление — облачные вычисления на GPU. Например, такие гиганты как Amazon, IBM и Google сдают свои вычислительные мощности на GPU в аренду. Сегодня с уверенностью можно сказать что будущее высокопроизводительных параллельных вычислений будет принадлежать GPU кластерам.
    ComBox Technology
    14,00
    Системы с иммерсионным охлаждением для майнинга
    Поделиться публикацией

    Комментарии 46

      –2
      OpenCL — ох, ноу…
        +7
        А что поделать, если нужна переносимость? Слышал, что CUDA приятнее, но написав один раз код на OpenCL его можно запустить как на CPU, так и на GPU от Intel, AMD, nVidia. Вроде даже на мобильных GPU можно. Да и не такой уж он и страшный.
        +2
        Первый процессор, получивший действительно массовое распространение – это 8086 от компании Intel, разработанный в 1978 году. Тактовая частота работы 8086 составляла всего 8 МГц. Спустя несколько лет появились первые процессоры внутри которых было 2, 4 и даже 8 ядер.
        А можно для тех, кто все проспал — что в 1980 году были за многоядерные процессоры с 2, 4 и даже 8 ядрами?
          +2
          Ну, 30 — это тоже «несколько», по сравнению со временем жизни Вселенной. ;)
            +2
            3,7 млрд лет назад на земле образовалась жизнь, а спустя несколько дней появились многоядерные процессоры.
            0
            С несколькими ядрами внутри — действительно не было. А вот технология SMP взяла старт с 486-х и применялась в серверных решениях. Правда это было уже на излете 486х, незадолго перед выходом Pentium Pro.
            +2
            Интересно было б сравнить производительность с реализацией на Cuda
              +6
              Да я вам и так скажу — на кластере AMD производительность куды будет равна 0)
                +1
                дык надо же на NV, оба сожрёт
              –2

              Интересно, почему OpenCL, а не Vulkan? Vulkan для GPGPU сегодня вроде как более современная и перспективная технология.

                +2
                А это, как раз написано: в целях совместимости.
                  +1
                  Opencl C и glsl compute shaders это всё таки разные вещи. Можно задействовать что-то такое — github.com/google/clspv но я в подобном пока не вижу большого смысла. Плюс я так понимаю в статье чисто вычислительная задача.
                  +2

                  Ну хотя бы строчку кода...

                    0
                    майнеры поняли что крипту майнить на своих фермах бессмысленно и решили проводить вычисления.
                      0
                      Вы правы сейчас не лучшее время для майнинга.
                      IMHO майнеры не смогут занять нишу параллельных вычислений — так как среднестатистические 6-8 видеокарт это слишком мало для серьёзных расчётов. Плюс надо иметь штат программистов, чтобы писать поставленные задачи под OpenCL.
                      К тому же вся система должна быть специально спроектирована под параллельные вычисления.
                      Да и заказчики расчётов — в основном госструктуры и к ним приближенные, а они не будут работать с частниками.
                      В общем, если и дальше курс крипты будет проседать, то в продаже начнёт появляться всё больше и больше майнинг оборудования.
                      Не берём в расчёт ASIC'и — это вообще трудно будет продавать.
                      GPU хоть геймеры будут покупать, а вот куда девать машинку для расчётов SHA-256 я даже не представляю. :)
                      +1

                      А научный труд написан? Опубликован? Можно было раздел с литературой привести, если уж претендовать на описание решения научных штук...

                        0
                        Поскольку стою рядышком с процессом, позволю себе ответить за автора — опубликован основной научный труд, по которому проводилась текущая работа. Сейчас обсуждаются детали новой научной публикации в соавторстве, и она будет обязательно опубликована. Относительно раздела с литературой — согласен, есть куда стремиться в части представления материала. Видно, что тема очень интересна сообществу, но не хватает деталей.
                        +2
                        Такая интересная задача и такое плохое описание :( Ну вы же пишете не технический портал, а не на пикабу (при всём уважении к пикабу). Узкие технические подробности (например, про представление чисел) перемежаются с поэтическим описанием.

                        Сложность решения этой задачи в переборе огромного числа вариантов...

                        Ну что это за описание сложности? Ну неужели нельзя формулу написать?

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

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

                        В многопоточной среде скорость вычисления увеличилась в 5 раз… На этом этапе решение производило верные расчеты до n=80 за 10 минут, тогда как в Exсel’e эти расчеты занимали полтора месяца

                        Мне одному кажется, что 10 минут вместо 1.5 месяцев – это не в 5 раз? Или это, всё-таки, разные этапы?

                        Эта самая интересная часть проекта

                        А написано всего три абзаца и вообще не про неё :( Хотелось бы видеть основную часть статьи, как раз здесь. О планировщике задач, о профилировании OpenCL кода, о том, какие оптимизации на OpenCL делали, что сработало, а что нет. Вы же решали научную задачу, значит вас не должна связывать коммерческая тайна?

                        Здесь применён накопленный десятилетиями научный и практический опыт

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

                        О программировании GPU, особенно AMD информации очень мало во всём интернете, а тем более в рунете. И очень жаль, что статья, которая могла стать жемчужиной рунета, стала всего лишь рекламным постером кластера GPU.

                        UPD: И ни одного секрета так и не рассказали.
                          +1
                          Спасибо за лучший комментарий!
                          Согласен мало технических нюансов. Будем подтягивать уровень, поправим статью и указанные недочёты в ближайшее время.
                            0
                            Ну что это за описание сложности? Ну неужели нельзя формулу написать?


                            В худшем случае 2^n. Пути редуцирования (до 2^(n/2) примерно) не так интересны, это специфика задачи. К сожалению, статья раньше была в открытом доступе, а сейчас доступ только по подписке :(

                            О планировщике задач, о профилировании OpenCL кода, о том, какие оптимизации на OpenCL делали, что сработало, а что нет.


                            «Путевые заметки» остались, вопрос насколько это интересно. Там много спорного и, к сожалению, немало негатива — видно что AMD технология уже не так интересна как прежде. Инструментарий заброшен, компилятор сломал всю обратную совместимость, APP SDK с сайта не скачать.
                            Подозреваю, что бросили все силы на Vulkan…
                              0
                              «Путевые заметки» остались, вопрос насколько это интересно.

                              Очень даже интересно. Обязательно публикуйте!

                              К сожалению, статья раньше была в открытом доступе, а сейчас доступ только по подписке

                              Ссылкой поделитесь? Возможно, у меня есть подписка.
                                0
                                Ссылкой поделитесь? Возможно, у меня есть подписка.

                                mi.mathnet.ru/dm1388
                                С части IP из России открывается, с части нет
                                0
                                Вообще, подробностей хотелось бы побольше. И математики и программирования и устройства кластера.
                              0
                              полтора месяца до n=80 в Excel;
                              час до n=80 на Core i5 с оптимизированной программой на С++;
                              10 минут до n=80 на Core i5 с использованием многопоточности;
                              10 минут до n=100 на одном GPU AMD RX 480;
                              120 минут до n=127 на ComBox A-480.

                              Excel считал примерно в 24*45=1080 раз медленнее, чем "оптимизированная программа на С++". Мне казалось, "скриптовые языки" работают не настолько медленно.


                              Уточните пожалуйста, сколько времени считалось на GPU при n=80 ?

                                +1
                                При переходе из Excel к C++ поменяли способ хранения данных. В Excel каждая последовательность была представлена массивом чисел (набором ячеек), а на C++ задействовали uint256 и закодировали последовательность в бинарном виде. Если в Excel при проверке на наложение со сдвигом необходимо было перебирать все члены массива, то на C++ это просто битовые операции — rotl, and.
                                Количество переборов тоже снизили, многие комбинации заведомо не являются решением.
                                +1
                                А зачем вы так сильно накрутили лайки в публикации поста в группе Хабра в ВК?
                                  +1

                                  Зашёл в статью только чтобы узнать, ради чего накрутки

                                    0
                                    Зашёл в ВК только чтобы узнать где накрутили. :)
                                    Больше 1100 лайков! Это или пиарщики жгут или «подарок» прилетел.
                                    Но это же не продающий пост, а просто техническая статья.
                                    И зачем накручивать? Крайне не понятно.
                                      0
                                      Может стараются особо страстные студенты «Чуднова А.М.».
                                        0
                                        Может быть. Так сказать, сдают зачёт. :))))
                                  0

                                  У меня не сошлось вот это:
                                  час до n=80 на Core i5 с оптимизированной программой на С++;
                                  10 минут до n=80 на Core i5 с использованием многопоточности;


                                  Ваш Core i5 был 6-ядерный?

                                    0
                                    Первый вариант работал в четыре потока + диспетчер.
                                    Дополнительный прирост скорости образовался из-за слияния функций. Видимо более компактный код компилятору проще оптимизировать.
                                    К примеру, SQLite не зря делают Amalgamation — они говорят о росте производительности до 5%
                                      0

                                      Могло проявиться т.н. "сверхлинейное ускорение", например если данные длиной M не влезали в кэш, а длиной M/4 начали влезать.

                                      0
                                      Имхо, будущее параллельных вычислений за туманными технологиями.
                                        0
                                        Тактовая частота работы 8086 составляла всего 8 МГц.


                                        4.77 или типа того :-) Даже первые 286-е на 6 МГц жили :-)
                                          0
                                          Было несколько модификаций, 8086-1 работал на 10 Мгц
                                            0
                                            Да, я знаю и помню. В данном контексте имеет смысл говорить о худшем случае, хотя это мое личное мнение. Строго говоря, наибольшую популярность вообще 8088 получил.
                                              0
                                              Соглашусь, тут мы допустили небрежность. Изначально хотели больше написать про x86 и историю, но потом этот текст ушел, т.к. все-таки статья о другом.
                                          0
                                          Простите возможно за глупые вопрос, но как вы распределяете задачи и данные по видео картам в кластере?
                                            0
                                            У нас в одном вычислительном юните 12 GPU, данные на них мы загружали из управляющей программы на языке C. На OpenCL это делается просто — в каждую карту загружается массив входных векторов. Именно задачи тут распределять не нужно, каждый юнит может считать свою последовательность, т.к. решение короткое по времени.
                                            Между юнитами загрузка очень простая, именно для этого случая просто скрипт на питоне.
                                              0
                                              А процессор, случайно, не Celeron?
                                                0
                                                Celeron и младшие i3
                                            +1
                                            Первый процессор, получивший действительно массовое распространение – это 8086 от компании Intel, разработанный в 1978 году.

                                            Ну это мягко говоря не так — до него были Intel 8080, MOS 6502, Zilog Z80.
                                              0
                                              Извините за неточность, конечно же — Первый 16-битный процессор.
                                              0

                                              Очень интересная тема. Но хотелось бы более красочного оформления — как уже писали, было бы отлично вставить графики, формулы, диаграмы и т.д. Математика мне кажется не была бы лишней здесь.
                                              Описано так, будто хотят обьяснить это очень поверхностно, буквально для рандомного прохожего, который возможно слышал про эксель, и что "процессор" это не коробка "кампутера", а отдельный элемент, как и гпу.

                                                0
                                                Спасибо за комментарий. Приняли к сведению, исправимся.

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

                                              Самое читаемое