LINUX.ORG.RU

[C++][templates] преобразование элементов контейнера на лету

 


0

1

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

Пока в контейнере даблы, или типы для которых перегружены необходимые арифметические операции, все работает. Но возникает необходимость обрабатывать: 1) некоторое поле структуры (элемента контейнера) 2) результат вызова некоторой сторонней ф-ии для структуры

напр, в контейнере лежат структуры

struct cell{ double rho, T; };

double energy( const cell& c ){ return rho*T; }
я хочу проинтерполировать отдельно rho и отдельно результаты вызова energy.

Вопрос - как правильно организовать ф-ю интерполяции (она шаблонная) что бы не было накладных расходов и оверхеда по коду?

Мне пока пришло в голову только такое решение:

template <class T> struct acces_as_is{
typedef r_type T;
static const T get( const T& x){ return x; }
};

template <class C, typename A=access_as_is<typename C::cell_type> > typename A::type_r interpolate ( const C & arr, ...){ 
...
... = A::get( arr[...] ) ; 
...
}

C::cell_type - тип элемента в контейнере. Но у меня смутное ощущение, что я изобретаю велосипед... да и использование будет выглядеть кривовато.

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

В этом случае на каждый вызов будет теряться скока то тактов + будет вылетать конвейр? Тут важна производительность (кроме удобства).

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

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

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

Если ее передали через аргумент interpolate, то как ее компилятор встроит? Можно пример?

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

Если ее передали через аргумент interpolate, то как ее компилятор встроит?

Да, но не функцию, а функциональный объект, тип которого является аргументом шаблона interpolate. Ты ведь тоже рассчитываешь, что get в твоём примере будет встроена.

template<typename C, typename F>
auto interpolate(const C& arr, F acc, ...) -> decltype(acc(arr[0])
{
 ...
 ... = acc(arr[...]);
 ...
}

interpolate(carr, [](const Cell& cell) { return cell.foo; });
interpolate(carr, std::mem_fn(&Cell::foo));

Всё так же как в STL, у компилятора есть всё необходимое для встраивания функции.

Begemoth ★★★★★
()

Кажется, ты изобретаешь map/foreach

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

Да, так вроде нормально... Спасибо!

AIv ★★★★★
() автор топика

Судя по названиям переменных CFD/FEM ? :)

Не поддавайся на уловки плюсатых :) Юзай православный FORTRAN :)

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

Нет, это моя библиотека.

Я и сам плюсат, а фортран ИМНО применим только для чего то ну очень примитивного;-)

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

>Нет, это моя библиотека.

Ну понятно что не Пушкина :)

Я вообще -то про предметную область :)

а фортран ИМНО применим только для чего то ну очень примитивного;-)

А пацаны из всяких NASA etc. в курсе уже ? :)

ЗЫ: Качните последний OpenFOAM, там есть много полезного для вашей велосипедной фабрики :)

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

> Я вообще -то про предметную область :)

Числ моделирование всего сущего;-)

А пацаны из всяких NASA etc. в курсе уже ? :)

Я даже и не знаю... они ЛОР читают? www.linux.org.ru/wiki/en/User:AIv/LRnLA

ЗЫ: Качните последний OpenFOAM, там есть много полезного для вашей велосипедной фабрики :)

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

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

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

Узнаю молодую но дерзкую поросль :))

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

Да уж, я на ЛОР зайдешь, про фортран услышишь, и так вот сразу молодеешь... ;-)

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

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

>Вы по ссылочке то сходите

Сходил :) Похоже на описание вечного двигателя :)

Насколько я понял пробежав по диагонали текст, попытка представить параллельную задачу в виде распределённой ?

судя по Вашей аватарке

Ну она какбы намекает :)

Про применимость фортрана (неявно) - самый посл абзац.

Я бы был аккуратнее с суждениями про фортран и про его неприменимость (хотя сам его не использую с начала 90-х)

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

> Похоже на описание вечного двигателя :)

Гыы... Если уж так, это описание РАБОТАЮЩЕГО вечного двигателя (точнее 5 разных моделей). Научно-популярное, на бол. детальное описание там есть ссылки.

попытка представить параллельную задачу в виде распределённой ?

Нет, это просто изменение порядка выполнения операций явной числ схемы, позволяющего увеличить производительность на неск порядков. И да, на фортране ИМНО это сделать нельзя. Т.е. в принципе можно, но реализация будет настолько сложна, что можно считать что нельзя;-)

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

И безотносительно к LRnLA - в посл годы весьма «конкретные пацаны» пишущие на фортране и являющиеся реально крупными спецами в своих областях почему то приходят ко мне и предлагают чего то им сделать, причем платят за это деньги (хотя могли бы сами сделать и деньги взять себе?).

Я пишу на С++/Python, и вот думаю - то ли я такой очень умный, то ли с фортраном что то не то... из скромности грешу на фортран;-)

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

>Нет, это просто изменение порядка выполнения операций явной числ схемы,

Звучит дико :)

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

Им просто надоело заниматься тем чем должна заниматься молодёжь (кодить на) :)

Гыы... Если уж так, это описание РАБОТАЮЩЕГО вечного двигателя (точнее 5 разных моделей)

Судя по всему приведённые модели просто хорошо ложаться на парадигму :) Не факт что остальные будут столь же хорошо это делать :)

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

> Звучит дико

Те, кто знакомятся с LRnLA обычно проходят три стадии:

1) дикость,бред, я всю жизнь этим занимаюсь, этого не может быть. 2) УХ ТЫ!!! 3) ой ееееееее....

Вы пока на первой.

Судя по всему приведённые модели просто хорошо ложаться на парадигму :) Не факт что остальные будут столь же хорошо это делать :)

На эту парадигму ложатся ВСЕ модели, в числ. реализациях которых скорость распространения возмущений конечна. Как бы оно очевидно (легко доказывается). Если Вы картинку на аватарке считали по неявной схеме - оно не ляжет. По явной - ляжет... если конечно Вы захотите потратить много времени и сил, для того что бы поднять производительность своего кода на неск порядков;-) Ну или если Вам уже лень кодить, а хочется сделать супер-пупер-код (и у Вас есть деньги) - велкам;-)))

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

Идею я примерно понял. Проблема в куче ляпов которые я наблюдаю в приведённых текстах.

В том числе «изменение порядка операций в явной численной схеме»

Там у вас меняется меняется не «порядок операций» (иначе это уже другая ЧС) а порядок перебора узлов

Ну и куча других ляпов которые царапают слух/взгляд Например: «Существенно ухудшает ситуацию организация данных в традиционные многомерные массивы - для задач с D>1, ячейки расположенные рядом в пространстве находятся на большом удаление в памяти.» - вы представляете как работает кеш современного процессора ? Там термин «рядом» как раз лежит в плоскости времени и почти никак (с точностью до строки кеша) не связан с расположением ячейки в памяти.

PS: Аватарка действительно считалась по явной численной схеме но на ваш алгоритм не ляжет ввиду полного отсутствия LR :)

ЗЫ: Почему бы вам не бросить вашу ссылку на профессиональный форум, например на http://www.cfd-online.com/Forums/main/

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

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

Как бы многие арифметические операции коммутативны;-) Вы правы насчет перебора узлов, спасибо критику.

Насчет далеко-рядом: да, я представляю как работает кэш. И для трад массива по одному направлению рядом в памяти означает быстрый доступ (потому что страница та же и оно в кэше уже), а по другим направлением далеко означает разные страницы и тд (там иерархическая структура, у памяти то), и очень медленный доступ. О что все и бьются в первую очередь. Во вторую очередь бьются о низкую ПСП памяти, вот тут и нужен LRnLA.

Аватарка действительно считалась по явной численной схеме но на ваш алгоритм не ляжет ввиду полного отсутствия LR

Если схема явная, то наск я представляю CFD скорость таки конечна, и LR там есть. Основная наша проблема - зашоренность грамотных специалистов. А CFD мы пока не занимаемся... хотя вот сейчас у автора LRnLA студент м.б. будет делать диплом на эту тему.

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

Кстати и у кэша иерархическая структура. Ну да Вы то должны знать, если когда нить тестили зависимость эффективности своего кода от размера задачи, то для хорошего кода все эти уровни оч четко видны.

Хотя да, обычно грамотные специалисты видят для малых размеров задачи СВЕРХУСКОРЕНИЕ(!!!) - так вот это нормальная скорость работы, которая сразу проседает когда задача не лезет в верхний кэш. LRnLA коды работают с такой эффективностью для любых размеров задачи, в тч и когда задача не лезет в RAM;-)

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

И для трад массива по одному направлению рядом в памяти означает быстрый доступ (потому что страница та же и оно в кэше уже)

Вы просто не представляете каков размер узла(ячейки) в современных CFD кодах и как он соотносится с размером строки кеша :)

Для справочки размер ОДНОЙ ячейки (пример им моего текущего проекта)

sizeof(FlowNode3D<double,NUM_COMPONENTS>) = 1528

При размере строки кеша (L2) 64 байта (P4)

ЗЫ: Собственно поэтому она такого размера чтобы носить с собой все данные, которые необходимы на текущей итерации и кеш-эффекты при таком подходе ощущаются в полный рост, включая сверхлинейнеое ускорение, особенно на процессорах с большим L2/L3 кешами

Вообще при рандомном доступе критическим считается размер блока данных в 128 байт (по тестам)

и LR там есть

по иронии локальная рекурсия в CFD обычно применяется для несжимаемых (бесконечная скорость распространения возмущения) случаев в неявных и полунеявных схемах :)

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

>грамотные специалисты

для малых размеров задачи

:))

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

> Для справочки размер ОДНОЙ ячейки (пример им моего текущего проекта)

sizeof(FlowNode3D<double,NUM_COMPONENTS>) = 1528

Для у-й Власова-Максвелла размер ячейки сравним. И сейчас работает 3D3V LRnLA код, хотя в MIT было неск диссертаций защищено, где в частности утверждалось, что решение подобных задач на совр комп. невозможно. Кроме неск уровней кэша в RAM есть еще уровни, про диск и обмены в кластере я не говорю;-)

по иронии локальная рекурсия в CFD обычно применяется для несжимаемых (бесконечная скорость распространения возмущения) случаев в неявных и полунеявных схемах :)

Это наск я понимаю другая история. И там LR по пространству (?), а тут LR по пространству-времени.

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

> И там LR по пространству (?),

Нет, там локальность связана с алгоритмом коррекции давления в ячейке

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

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

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

В широком смысле

Реку́рсия — процесс повторения чего-либо самоподобным способом

то есть в ЯКРМ рекурсией будет повторение операций численного интегрирования на следующем временном шаге

а например в SIMPLE алгоритме шаг коррекции давления тоже вполне себе рекурсией (и гораздо более локальной)

Ваша идея с локальной рекурсией понятна, но меня в ней например смущает то что потоки на границах КО при попытке посчитать по такому алгоритму будут мягко говоря не соответствовать действительности.

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

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

Схема явная, шаблон скажем только ближ соседи. Дальше все - LRnLA числ. схему не меняет, а меняет только порядок обхода узлов. Все арифметич действия (я не про ячейку а про всю область) остаются ровно теми же, меняется только их порядок, причем порядок меняется так, что бы ответ был такой же что и при трад обходе, но локальность данных была выше -> выше эффективность.

AIv ★★★★★
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.