Re[22]: Реальная производительность WebAssembly?
От: Serginio1 СССР https://habrahabr.ru/users/serginio1/topics/
Дата: 19.09.17 08:09
Оценка:
Здравствуйте, Ikemefula, Вы писали:

I>Здравствуйте, Serginio1, Вы писали:


S>>Лучше взять эти тесты


I>О, круто, вот то что надо! И ты, конечно, портируешь их на JS, дабы мы могли созерцать разницу в перформансе ?


Ну там немного трудов то. Было бы время сделал. Я люблю тесты и написал бы на TS http://electricessence.github.io/TypeScript.NET/
https://github.com/electricessence/TypeScript.NET

Но увы
и солнце б утром не вставало, когда бы не было меня
Отредактировано 19.09.2017 8:23 Serginio1 . Предыдущая версия . Еще …
Отредактировано 19.09.2017 8:21 Serginio1 . Предыдущая версия .
Отредактировано 19.09.2017 8:21 Serginio1 . Предыдущая версия .
Отредактировано 19.09.2017 8:10 Serginio1 . Предыдущая версия .
Re[23]: Реальная производительность WebAssembly?
От: Ikemefula Беларусь http://blogs.rsdn.org/ikemefula
Дата: 19.09.17 08:24
Оценка:
Здравствуйте, Serginio1, Вы писали:

S> Ну там немного трудов то. Было бы время сделал. Я люблю тесты и написал бы на TS http://electricessence.github.io/TypeScript.NET/

S>https://github.com/electricessence/TypeScript.NET

А, ну ясно, трудов немного, но времени надо очень много. Спасибо, кеп!
Re[24]: Реальная производительность WebAssembly?
От: Serginio1 СССР https://habrahabr.ru/users/serginio1/topics/
Дата: 19.09.17 08:29
Оценка:
Здравствуйте, Ikemefula, Вы писали:

I>Здравствуйте, Serginio1, Вы писали:


S>> Ну там немного трудов то. Было бы время сделал. Я люблю тесты и написал бы на TS http://electricessence.github.io/TypeScript.NET/

S>>https://github.com/electricessence/TypeScript.NET

I>А, ну ясно, трудов немного, но времени надо очень много. Спасибо, кеп!


Там код на TS один в один C# повский. При этом кода то всего раз два и обчелся. Возьми хотя бы
http://rsdn.org/forum/dotnet/6808392.1
Автор: Serginio1
Дата: 13.06.17


первый тест

public class Test

{

    public static void Main()

    {

        while (true)

        {

            var q = new Queue<int>();

            var sw = Stopwatch.StartNew();

            for (int i = 0; i < 100_000_000; i++)

            {

                q.Enqueue(i);

                q.Dequeue();

            }

            Console.WriteLine(sw.Elapsed);

        }

    }

}


его трудно на TS перевести?

Кстати а как в Node.js с многопоточностью? Можно еще и parallel foreach проверить
и солнце б утром не вставало, когда бы не было меня
Отредактировано 19.09.2017 8:32 Serginio1 . Предыдущая версия .
Re[25]: Реальная производительность WebAssembly?
От: Ikemefula Беларусь http://blogs.rsdn.org/ikemefula
Дата: 19.09.17 08:32
Оценка:
Здравствуйте, Serginio1, Вы писали:

S>первый тест

...
S> его трудно на TS перевести?

Трудно, у тебя же на это времени нет, правильно ?
Re[26]: Реальная производительность WebAssembly?
От: Serginio1 СССР https://habrahabr.ru/users/serginio1/topics/
Дата: 19.09.17 08:53
Оценка:
Здравствуйте, Ikemefula, Вы писали:

I>Здравствуйте, Serginio1, Вы писали:


S>>первый тест

I>...
S>> его трудно на TS перевести?

I>Трудно, у тебя же на это времени нет, правильно ?


Нет. Просто вы тратите время, а я предложил варианты.
Ну не надо, так не надо
и солнце б утром не вставало, когда бы не было меня
Re[18]: Реальная производительность WebAssembly?
От: alexzzzz  
Дата: 19.09.17 11:49
Оценка:
Здравствуйте, Ikemefula, Вы писали:

A>>Оптимизированная версия C#:

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

Никуда я его не убрал, а исправил на качественную реализацию:
Array.Sort(vals, new TestClass.TestClassComparer());

Я ж не буду "библиотечный" ToString переписывать на голом C# без необходимости. И Array.Sort не буду, если моя реализация сортировки для конкретной задачи не окажется вдруг эффективнее. В реальном проекте я естественно выкину 30 строк нетривиального кода и заменю на одну тривиальную, если она не медленнее. А если быстрее, так вообще отлично. Постоянно так делаю.

A>>Одинаково.

I>Да, серьезный тест, практичный и реальный.

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

A>>1. Я не вижу в коде никого, кому были бы нужны строковые представления гуидов. Ни одного их потребителя. Разве что TestClass.ToString, но и тот нигде не вызывается.

A>>2. Guid — value-тип длинной 16 байт. В виде строки он занимает (навскидку) 32*2+6 байт + оверхед + 4/8 байт под ссылку на эту строку. Гуиды экономнее аналогичных строк раз в пять.
I>А что, конверсия в строку при каждом доступе ничего не стоит ?

Конверсия в строку ничего не стоит, если она никогда не происходит. А тут она никогда не происходит.

I>Кроме того, в тесте ведь не важно, что в строке. Главное что бы одинаково в обоих языках и были более-менее случайные символы.


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

Если бы там были строки, содержащие не гуиды, а что-то другое (например, автомобильные номера), я бы тоже делал сортировку с учётом этого знания.

I>Тест он про сортировку массива объектов, у которых есть строковые свойства. Гуиды там или не гуиды, дело десятое.


В строках всегда содержится что-то конкретное. Как минимум, обычно заранее понятно, нужна для их сортировки культура или не нужна.
Re[25]: Реальная производительность WebAssembly?
От: alexzzzz  
Дата: 19.09.17 11:51
Оценка:
Здравствуйте, Serginio1, Вы писали:

S> Там код на TS один в один C# повский. При этом кода то всего раз два и обчелся. Возьми хотя бы

S>http://rsdn.org/forum/dotnet/6808392.1
Автор: Serginio1
Дата: 13.06.17

S>первый тест
S>
S>public class Test
S>{
S>    public static void Main()
S>    {
S>        while (true)
S>        {
S>            var q = new Queue<int>();
S>            var sw = Stopwatch.StartNew();
S>            for (int i = 0; i < 100_000_000; i++)
S>            {
S>                q.Enqueue(i);
S>                q.Dequeue();
S>            }
S>            Console.WriteLine(sw.Elapsed);
S>        }
S>    }
S>}
S>

S> его трудно на TS перевести?

Это микробенчмарки. Они дают приблизительно понять, сколько стоит то или иное действие; что более эффективнее, что менее. Такие тесты, не выполняющие полезной работы, интересны в рамках одного языка. У меня рука так и тянется выкинуть внутренний цикл нафик, потому что работать будет быстрее, а для внешнего наблюдателя ничего не изменится.
Re[26]: Реальная производительность WebAssembly?
От: Serginio1 СССР https://habrahabr.ru/users/serginio1/topics/
Дата: 19.09.17 11:56
Оценка:
Здравствуйте, alexzzzz, Вы писали:


A>Это микробенчмарки. Они дают приблизительно понять, сколько стоит то или иное действие; что более эффективнее, что менее. Такие тесты, не выполняющие полезной работы, интересны в рамках одного языка. У меня рука так и тянется выкинуть внутренний цикл нафик, потому что работать будет быстрее, а для внешнего наблюдателя ничего не изменится.


как раз работа с очередями, коллекциями одни из основных рабочих алгоритмов.
Заметь на сколько они быстрее в .Net Core
и солнце б утром не вставало, когда бы не было меня
Re[25]: Реальная производительность WebAssembly?
От: alexzzzz  
Дата: 19.09.17 12:04
Оценка: 2 (1)
Здравствуйте, Serginio1, Вы писали:

S> Кстати а как в Node.js с многопоточностью? Можно еще и parallel foreach проверить


Как в Node.js не знаю, а в C# как раз собирался проверить:

  C#
using System;
using System.Diagnostics;
using System.Linq;

namespace QuickSort
{
    public class Program
    {
        public static void Main(string[] args)
        {
            var watch = new Stopwatch();
            for (int i = 0; i < 5; i++)
            {
                watch.Restart();
                var vals = Enumerable.Range(0, 1000 * 1000).AsParallel().Select(x => new TestClass()).ToArray();
                watch.Stop();
                Console.WriteLine("Total secs: " + watch.Elapsed.TotalSeconds);
            }
            Console.WriteLine($"GC: {GC.CollectionCount(0)} {GC.CollectionCount(1)} {GC.CollectionCount(2)}");
            Console.ReadLine();
        }
    }

    internal class TestClass
    {
        public string Id = CreateGuid();
        public string Value = CreateGuid();
        private static readonly Random gen = new Random();

        private static string CreateGuid() => gen.Next(100000000).ToString("0000000000");
    }
}


Total secs: 0,2958201
Total secs: 0,398753
Total secs: 0,3198091
Total secs: 0,4641866
Total secs: 0,4886261
GC: 109 41 8

4-ядерник без гипертрединга. Большой разброс на таком коротком тесте. Первый результат стабильно 0.30±0.01, а дальше пляшет.
Re[26]: Реальная производительность WebAssembly?
От: Serginio1 СССР https://habrahabr.ru/users/serginio1/topics/
Дата: 19.09.17 12:17
Оценка:
Здравствуйте, alexzzzz, Вы писали:

A>Здравствуйте, Serginio1, Вы писали:


S>> Кстати а как в Node.js с многопоточностью? Можно еще и parallel foreach проверить


A>Как в Node.js не знаю, а в C# как раз собирался проверить:



A>Total secs: 0,2958201

A>Total secs: 0,398753
A>Total secs: 0,3198091
A>Total secs: 0,4641866
A>Total secs: 0,4886261
A>GC: 109 41 8

A>4-ядерник без гипертрединга. Большой разброс на таком коротком тесте. Первый результат стабильно 0.30±0.01, а дальше пляшет.


То есть если сравнивать с
Total: 567 ms
Total: 652 ms
Total: 641 ms
Total: 606 ms
Total: 638 ms
То максимальный прирост в 2 раза?
Ну это нормально. Там процессор еще на чтонибудь расходуется.
Спасибо!
и солнце б утром не вставало, когда бы не было меня
Re[19]: Реальная производительность WebAssembly?
От: Ikemefula Беларусь http://blogs.rsdn.org/ikemefula
Дата: 19.09.17 12:18
Оценка:
Здравствуйте, alexzzzz, Вы писали:

A>>>Оптимизированная версия C#:

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

A>Никуда я его не убрал, а исправил на качественную реализацию:

A>
Array.Sort(vals, new TestClass.TestClassComparer());


Это другой тест, он показыавет, какая из библиотечных функций качественнее сделана.
А предыдущий показывал какой из компилеров даёт более качественный код.


A>>>1. Я не вижу в коде никого, кому были бы нужны строковые представления гуидов. Ни одного их потребителя. Разве что TestClass.ToString, но и тот нигде не вызывается.

A>>>2. Guid — value-тип длинной 16 байт. В виде строки он занимает (навскидку) 32*2+6 байт + оверхед + 4/8 байт под ссылку на эту строку. Гуиды экономнее аналогичных строк раз в пять.
I>>А что, конверсия в строку при каждом доступе ничего не стоит ?

A>Конверсия в строку ничего не стоит, если она никогда не происходит. А тут она никогда не происходит.


Ага, ты сравниваешь гуиды. Так ? То есть, вместо "объект со строковыми филдами" ты влупил другой тест "объект с гуидами"
То есть, ты подменяешь яблоки грушами.

I>>Кроме того, в тесте ведь не важно, что в строке. Главное что бы одинаково в обоих языках и были более-менее случайные символы.


A>В тесте важна скорость получения результата. У исходной программы на входе ничего нет, а на выходе упорядоченная коллекция элементов, состоящих из двух гуидов, отсортированая по первому гуиду. И раз там гуиды, сравнивать их в виде строк довольно глупо, я считаю.


Оригинальный код принимает на вход данные в виде массива объектов со строковыми филдами.
Ты поменял данные в пользу C# версии.

A>Если бы там были строки, содержащие не гуиды, а что-то другое (например, автомобильные номера), я бы тоже делал сортировку с учётом этого знания.


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

I>>Тест он про сортировку массива объектов, у которых есть строковые свойства. Гуиды там или не гуиды, дело десятое.

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

В тестах принято входные данные не изменять, не подгонять под нужный результат.
Re[26]: Реальная производительность WebAssembly?
От: Ikemefula Беларусь http://blogs.rsdn.org/ikemefula
Дата: 19.09.17 12:19
Оценка:
Здравствуйте, alexzzzz, Вы писали:

A>Это микробенчмарки. Они дают приблизительно понять, сколько стоит то или иное действие; что более эффективнее, что менее. Такие тесты, не выполняющие полезной работы, интересны в рамках одного языка. У меня рука так и тянется выкинуть внутренний цикл нафик, потому что работать будет быстрее, а для внешнего наблюдателя ничего не изменится.


Даже с разными языками можно сравнивать, главное данные не подгонять под тест.
Re[25]: Реальная производительность WebAssembly?
От: Ikemefula Беларусь http://blogs.rsdn.org/ikemefula
Дата: 19.09.17 12:21
Оценка: 2 (1)
Здравствуйте, Serginio1, Вы писали:

S> Кстати а как в Node.js с многопоточностью? Можно еще и parallel foreach проверить


Смешно — джаваскрипт выполняется ровно в одном потоке, хотя vm и многопоточная.
Re[27]: Реальная производительность WebAssembly?
От: alexzzzz  
Дата: 19.09.17 12:33
Оценка: 2 (1)
Здравствуйте, Serginio1, Вы писали:

S> То максимальный прирост в 2 раза?

S> Ну это нормально. Там процессор еще на чтонибудь расходуется.

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

  C#
using System;
using System.Diagnostics;
using System.Threading;

namespace QuickSort
{
    public class Program
    {
        private static int threadCount;
        private static ManualResetEvent waitHandle = new ManualResetEvent(false);

        public static void Main(string[] args)
        {
            const int ARRAY_SIZE = 1000 * 1000;
            const int THREADS = 4;

            var watch = new Stopwatch();
            for (var i = 0; i < 5; i++)
            {
                watch.Restart();
                waitHandle.Reset();

                var vals = new TestClass[ARRAY_SIZE];
                for (var j = 0; j < THREADS; j++)
                {
                    int segmentIndex = j;
                    ThreadPool.QueueUserWorkItem(_ => Fill(vals, segmentIndex * (ARRAY_SIZE / THREADS), ARRAY_SIZE / THREADS));
                }
                waitHandle.WaitOne();

                watch.Stop();
                Console.WriteLine($"Total: {watch.ElapsedMilliseconds} ms");
            }
            Console.WriteLine($"GC: {GC.CollectionCount(0)} {GC.CollectionCount(1)} {GC.CollectionCount(2)}");
            Console.ReadLine();
        }

        private static void Fill(TestClass[] array, int start, int count)
        {
            Interlocked.Increment(ref threadCount);

            int end = start + count;
            for (int i = start; i < end; i++)
            {
                array[i] = new TestClass();
            }

            Interlocked.Decrement(ref threadCount);
            if (threadCount == 0)
            {
                waitHandle.Set();
            }
        }
    }

    internal class TestClass
    {
        public string Id = CreateGuid();
        public string Value = CreateGuid();
        private static readonly Random gen = new Random();

        private static string CreateGuid() => gen.Next(100000000).ToString("0000000000");
    }
}

Total: 302 ms
Total: 262 ms
Total: 368 ms
Total: 359 ms
Total: 384 ms
GC: 109 41 7

Надеюсь, не накосячил.
Отредактировано 19.09.2017 13:00 alexzzzz . Предыдущая версия .
Re[20]: Реальная производительность WebAssembly?
От: alexzzzz  
Дата: 19.09.17 12:59
Оценка:
Здравствуйте, Ikemefula, Вы писали:

A>>Никуда я его не убрал, а исправил на качественную реализацию:

A>>
Array.Sort(vals, new TestClass.TestClassComparer());

I> Это другой тест, он показыавет, какая из библиотечных функций качественнее сделана.
I>А предыдущий показывал какой из компилеров даёт более качественный код.

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

Если стоит задача из положения планет на небе получить число 42, её правильное решение на C# будет выглядеть так:
int Solve(input) => 42;


A>>Конверсия в строку ничего не стоит, если она никогда не происходит. А тут она никогда не происходит.

I>Ага, ты сравниваешь гуиды. Так ? То есть, вместо "объект со строковыми филдами" ты влупил другой тест "объект с гуидами"
I>То есть, ты подменяешь яблоки грушами.

Я вижу, что на входе программы ничего нет, а на выходе отсортированные гуиды. Конечно буду использовать гуиды вместо строк. Если там целые числа, буду использовать целые числа. Это понятнее и тупо эффективнее.

I>Оригинальный код принимает на вход данные в виде массива объектов со строковыми филдами.

I>Ты поменял данные в пользу C# версии.

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

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


Входных данных нет. Время генерирования данных включено в измерения.
Re[21]: Реальная производительность WebAssembly?
От: alexzzzz  
Дата: 19.09.17 13:12
Оценка:
Здравствуйте, alex_public, Вы писали:

A>>Одинаково.

_>Подтверждаю. Для данного C# кода и данного JS кода, запущенного через node, у меня очень близкие цифры.
_>Только вот теперь рекомендую запустить этот же самый JS код в Firefox. Например с помощью такой странички:

386.5250000000001 мс
592.0699999999999 мс
311 мс
432.8299999999999 мс
488.1399999999999 мс
447.21000000000095 мс
432.85000000000036 мс
313.2049999999999 мс
435.1750000000011 мс
515.5900000000001 мс
447.8149999999987 мс
417.6749999999993 мс
415.6350000000002 мс
477.8299999999999 мс
435.47500000000036 мс
329.7999999999993 мс
443.6100000000006 мс
346.22999999999956 мс
361.0400000000009 мс
360.40000000000146 мс
Re[22]: Реальная производительность WebAssembly?
От: alex_public  
Дата: 19.09.17 13:34
Оценка:
Здравствуйте, alexzzzz, Вы писали:

_>>Подтверждаю. Для данного C# кода и данного JS кода, запущенного через node, у меня очень близкие цифры.

_>>Только вот теперь рекомендую запустить этот же самый JS код в Firefox. Например с помощью такой странички:

A>
386.5250000000001 мс
A>592.0699999999999 мс
A>311 мс
A>432.8299999999999 мс
A>488.1399999999999 мс
A>447.21000000000095 мс
A>432.85000000000036 мс
A>313.2049999999999 мс
A>435.1750000000011 мс
A>515.5900000000001 мс
A>447.8149999999987 мс
A>417.6749999999993 мс
A>415.6350000000002 мс
A>477.8299999999999 мс
A>435.47500000000036 мс
A>329.7999999999993 мс
A>443.6100000000006 мс
A>346.22999999999956 мс
A>361.0400000000009 мс
A>360.40000000000146 мс


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

Кстати, я тут ради развлечения засунул этот вроде как тест в C++, чтобы оценить насколько обсуждаемые языки отстают от максимальной производительности. И оказалось что не так уж и сильно. С конвертером строк из стандартной библиотеки получаем 130 мс. С быстрым конвертером из Boost'а получаем 70 мс, но это уже наверное "чит" (в обсуждаемых вариантах использовали только стандартную функцию).
Re[23]: Реальная производительность WebAssembly?
От: Serginio1 СССР https://habrahabr.ru/users/serginio1/topics/
Дата: 19.09.17 13:42
Оценка:
Здравствуйте, alex_public, Вы писали:



_>Кстати, я тут ради развлечения засунул этот вроде как тест в C++, чтобы оценить насколько обсуждаемые языки отстают от максимальной производительности. И оказалось что не так уж и сильно. С конвертером строк из стандартной библиотеки получаем 130 мс. С быстрым конвертером из Boost'а получаем 70 мс, но это уже наверное "чит" (в обсуждаемых вариантах использовали только стандартную функцию).


Еще раз не языки, а платформы. Тот же C# в трех платформах. .Net, .Net Core и Net Native. Там и компиляторы разные и CLR и без CLR
и солнце б утром не вставало, когда бы не было меня
Re[23]: Реальная производительность WebAssembly?
От: alexzzzz  
Дата: 19.09.17 14:14
Оценка:
Здравствуйте, alex_public, Вы писали:

_>Хм, странно, у меня ни одного значение более 300 мс нет. Похоже у нас всё же разные по производительности компьютеры и разные .net рантаймы (в начале из-за большого совпадения предыдущих цифр я подумал что одинаковые).


Core i5-2500K @4ГГц, рантаймы всякие есть, я запускал всё под Framework 4.0 в режиме x64.
Re[24]: Реальная производительность WebAssembly?
От: alex_public  
Дата: 19.09.17 15:36
Оценка:
Здравствуйте, alexzzzz, Вы писали:

_>>Хм, странно, у меня ни одного значение более 300 мс нет. Похоже у нас всё же разные по производительности компьютеры и разные .net рантаймы (в начале из-за большого совпадения предыдущих цифр я подумал что одинаковые).

A>Core i5-2500K @4ГГц, рантаймы всякие есть, я запускал всё под Framework 4.0 в режиме x64.

Хм, по идее не должно сильно отличаться. Ладно, мне что-то наскучило гадать, как и вообще вся эта темка. Просто покажу голые результаты всех этих тестов на своей машине, а кто хочет — пускай анализирует и разбирается. )))

C# (.Net 4.6.0081.0 x64):
Total secs: 0,5065547
Total secs: 0,6101966
Total secs: 0,5638938
Total secs: 0,5944783
Total secs: 0,6446389


JS (node.js v6.11.3):
Init: 598.240366 msecs
Init: 512.2526790000001 msecs
Init: 580.228163 msecs
Init: 580.1160620000003 msecs
Init: 512.322893 msecs


JS (Firefox 55.0.3 (64-бит))
251.38500000000022 мс
197.5050000000001 мс
257.28499999999985 мс
274.02000000000044 мс
204.35499999999956 мс


C++ (gcc 6.3.0)
139 мс.
138 мс.
139 мс.
139 мс.
138 мс.


C++ (gcc 6.3.0, функция конвертации числа в строку из Boost'а)
73 мс.
73 мс.
72 мс.
73 мс.
71 мс.


Процессор у меня Haswell Xeon 4 ГГц.
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.