LINUX.ORG.RU

Указатель на член класса являющий массивом и доступ к его (массива) элементам?

 


0

2

Такой вот изврат. Есть скажем структура

struct A{
   double x[10];
};
Я хочу указатель на член x (и доступ при разименовании к любому элементу), и/или указатель скажем на третий элемент (как указатель на член)
double A::*[10] p = &A::x;
double A::*p = &A::x [3];
че то в этом роде, но оно нефига не собирается (ни то ни то, на уровне синтакиса не так). Я могу конечно в ручную приводить типы и вычислять смещения, но хочется это делать Ъ...

★★★★★

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

Ок, «раз вы тут все такие умные», вот вопрос к тебе и к анонимусу по дизайну. Есть класс

template <class CELL> class BaseModel{
// туева хуча параметров
array<Cell,3> data; // трехмерный массив из Cell.
};

Cell может содержать один или несколько элементов типа Atom.

Atom может содержать пачку каких то полей, например

struct Atom{
    double x;
    float y[10];
};
Типы в общем любые POD, важно что это могут быть либо обычные поля, либо массивы с размером известным на момент компиляции (забыл как это прально зовется). Можно считать что Atom это POD тип или что то около того (точно НЕ виртуальный).

Теперича, мне нужен универсальный механизЪм, позволяющий вызвать для каждого атома некоторый метод BaseModel (или его наследника). Метод принимает Atom по ссылке + принимает сумму от некоторых полей соседей данного атома. Скажем сумму x-ов. Или сумму y[2]. У CELL структура и число атомов может быть очень разная, и только CELL знает как искать соседей. Я передаю CELL указатель на вызываемый метод BaseModel, всякую доп служебную информауцию, и мне надо передать каким то образом какие именно поля соседних атомов надо суммировать. Всякие виртуальный функции не предлагать, ПРОИЗВОДИТЕЛЬНОСТЬ КРАЙНЕ ВАЖНА.

Вы можете сказать «это изначально кривой дизайн». М.б., но этот кривой дизайн позволяет уменьшить число строк код на 1-2 порядка, пока других дизайнов не вижу.

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

Не, не путаю ни разу. Геттеры/сеттеры (пока они не виртуальные) не ухудшают производительность ни разу. Просто они усложняюи запутывают код, который и так очень запутанный.

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

UB на то и UB, что когда-то работает, а когда-то — нет.

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

и только CELL знает как искать соседей

Раз он такой умный, пусть сам и метод вызывает.

но этот кривой дизайн позволяет уменьшить число строк код на 1-2 порядка

Купите себе диск побольше для хранения исходников.

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

Раз он такой умный, пусть сам и метод вызывает.

Он и вызывает. Вопрос не в этом, вопрос в том как ему объяснить какие поля соседей суммировать. Ы?

Купите себе диск побольше для хранения исходников.

Дикс не вопрос. Но нужна будет еще пара десятков анонимусов с ЛОР-а, которые будут над этими исходниками работать за бесплатно. Возьметесь?

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

Я, конечно, сильно умный, но по поводу архитектуры не высказывался. Однако предположение том, что на входе POD, должно быть проверено; в Си++11 это ничего не стоит на этапе выполнения.

мне надо передать каким то образом какие именно поля соседних атомов надо суммировать

Указатель на объект + указатель на член. Но я не понимаю, зачем вообще кладж с union.

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

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

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

4.2, RTFM

Указатель на член класса не содержит указатель на объект - тут я конечно хрень написал, признаю. Но это не отменяет того факта, что указатель на член класс бесполезен без указателя на экземпляр класса.

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

Это зависит от того, что собственно хочется сделать. ВДруг у меня чиста академический интерес к размещению полей в классе?;-)

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

Если в качестве поля выступает элемент массива, на него не получается взять указатель как указатель на член

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

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

вопрос в том как ему объяснить какие поля соседей суммировать. Ы?

1. Разными методами Cell с вменяемыми названиями? 2. Политиками? 3. Получением итераторов? Выбирайте по вкусу.

Но нужна будет еще пара десятков анонимусов с ЛОР-а, которые будут над этими исходниками работать за бесплатно.

Зачем?

Возьметесь?

Мне мало того что платят, так ещё и за то, что я таких хакиров больно бью по пальцам металлической линейкой.

ЗЫЖ Чтобы убедиться в том, что программисты не такие страшные и иногда могут помочь, советую полистать «Предметно-ориенрованное проектирование» Эванса. Заодно научитесь задавать заказчику (в данном случае себе) правильные вопросы.

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

Это зависит от того, что собственно хочется сделать. ВДруг у меня чиста академический интерес к размещению полей в классе?;-)

А чем тогда offsetof() не устроил? Ну кроме того, что это C++11.

m0rph ★★★★★
()

1. Разными методами Cell с вменяемыми названиями?

Будет оверхед по коду. Cell-ов много разных.

2. Политиками?

Я ХЗ что это, можно пример?

3. Получением итераторов?

Это то сюда каким образом???

Но нужна будет еще пара десятков анонимусов с ЛОР-а, которые будут над этими исходниками работать за бесплатно.

Зачем?

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

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

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

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

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

А не зависят ли случаем складываемые поля от конкретного типа Atom? Если зависят — можешь подумать в сторону специализации шаблонной функции.

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

1-2. Я уже писал выше универсальный ответ — «шаблоны». Да, кода будет много (если он действительно нужен), но писать его будет компилятор. Вы же занимаетесь обратным: вместо однострочника GetXRef лепите приблизительно то, что сделает в этом случае компилятор, причём сделает правильно. И после этого рассказываете мне сказки о компактности своего кода. Политики (см Александреску, то ли первая, то ли вторая глава — читал очень давно) позволяют заворачивать в шаблоны не всё, а только выбор. В вашем случае — выбор того, какие поля в своих Atom-ах должен обработать Cell.

3. Если тот кто вызывает методы Cell знает какие использовать поля, но не знает какие внутри Atom-ы, он может попросить просто список Atom-ов и повыдёргивать из них нужные поля. Хотя, по сумбурному описанию вашей задачи видно, что править надо в другом месте.

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

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

А насильно кастовать к указателю на член нельзя, ЕМНИП.

Через reinterpret_cast<> можно вроде бы.

DELIRIUM ☆☆☆☆☆
()

Не делайте так, гады!

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

ЧТо сказать то хотели? В каком месте тут выстрелит выравнивание?

Не выравнивание или strict aliasing (разные вещи, про выравнивание вообще не было речи), а именно type punning. Там по ссылкам про то что по стандарту выставление одного поля union и использование другого это UB. Дальше — что в GCC это _не_ UB, но с другими компиляторами может быть баг (как в блоге qt пишут).

Выравнивание — если аллах точные числа дал, то всё ок, конечно :)

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

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

quasimoto ★★★★
()
Ответ на: Ваша же идея, но другими словами от anonymous

Дебажная сборка (без -O2, -O3) будет работать

Да по идее оно вообще должно работать (слишком много такого кода чтобы какой-то компилятор делал не так как нужно).

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

Дальше — что в GCC это _не_ UB, но с другими компиляторами может быть баг (как в блоге qt пишут).

А меня другие не интересуют;-)

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

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

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

Если тот кто вызывает методы Cell знает какие использовать поля, но не знает какие внутри Atom-ы, он может попросить просто список Atom-ов

Прямо вот так вот std::list<Atom*> получить?

Хотя, по сумбурному описанию вашей задачи видно, что править надо в другом месте.

Я могу конечно сказать, что речь идет о моделировании системы у-й Ландау-Лифшица атом-в-атом;-) И в каком же месте надо править?

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