Модераторы: bsa
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> вопрос про возможность языка, можно ли скопировать функцию 
V
    Опции темы
asmdzen
Дата 5.12.2010, 12:35 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата



**


Профиль
Группа: Участник
Сообщений: 345
Регистрация: 28.11.2010

Репутация: 3
Всего: 5



Привет всем! 
Проблема: создается новый поток (thread) которому передается указатель на функцию, нужно чтоб при создании каждого нового потока передавался указатель на функцию какогото обьекта. Нет никаких возможностей передавать указатель this функции.
Мое теоретическое решение: нужно при создании потока передавать ему адресс на копию глобальной функции где уже есть этот указатель this на нужный нам обьект, вот только я незнаю можно вообще это реализовать, пробовал при помощи шаблонов - ничего не получилось, писал примерно так:
Код

template<int *a> void myfunc()
{
    *a++;
}

static int xb[10];

int main() 
{
    myfunc<&xb[1]>();
    return 0;
}

выдает ошибку: invalid template argument for 'myfunc', expected compile-time constant expression.

Скажите пожалуйста это вообще возможно? если да то как?
PM MAIL   Вверх
Леопольд
Дата 5.12.2010, 13:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 943
Регистрация: 17.6.2009

Репутация: 3
Всего: 13



Цитата(asmdzen @  5.12.2010,  12:35 Найти цитируемый пост)
 создается новый поток (thread)
где код? 
Если поток создаётся при помощи boost::thread или С++0x std::thread, то это делается довольно просто. Если средствами ОС, то надо дополнительно написать код.


Это сообщение отредактировал(а) Леопольд - 5.12.2010, 13:23


--------------------
вопросов больше чем ответов
PM MAIL   Вверх
asmdzen
Дата 5.12.2010, 13:30 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата



**


Профиль
Группа: Участник
Сообщений: 345
Регистрация: 28.11.2010

Репутация: 3
Всего: 5



Леопольд, код слишком большой, да и выглядит он неочень, не используются ни boost ни C++0x.
Вообщето проблема состоит именно в том что у меня нет доступа к функции создающей поток, я ей передаю указатель на функцию которая будет вызыватся из созданного потока с определенными параметрами к которым у меня тоже нет доступа. Вобщем это call-back функция, которую я хочу сделать членом какогото обьекта (не static в классе).
PM MAIL   Вверх
Леопольд
Дата 5.12.2010, 13:38 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 943
Регистрация: 17.6.2009

Репутация: 3
Всего: 13



Цитата(asmdzen @  5.12.2010,  12:35 Найти цитируемый пост)
выдает ошибку: invalid template argument for 'myfunc', expected compile-time constant expression.
В параметрах шаbлона нельзя передавать указатель на переменную. Но можно передавать указатель/ссылку на функцию.
http://codepad.org/7JjXSXkR

Добавлено @ 13:40
Цитата(asmdzen @  5.12.2010,  13:30 Найти цитируемый пост)
Вообщето проблема состоит именно в том что у меня нет доступа к функции создающей поток, я ей передаю указатель на функцию которая будет вызыватся из созданного потока с определенными параметрами к которым у меня тоже нет доступа. Вобщем это call-back функция, которую я хочу сделать членом какогото обьекта (не static в классе). 
Напиши минимальный код, который треbуется. Нужно, хотя bы, увидеть интерфейс который ты используешь (т.е. все сигнатуры функций). Пока не до конца понятно, что именно надо.

Недавно поднималась тема про колbяки 
http://forum.vingrad.ru/forum/topic-316218.html
Может что-то похожее?


Это сообщение отредактировал(а) Леопольд - 5.12.2010, 13:51


--------------------
вопросов больше чем ответов
PM MAIL   Вверх
asmdzen
Дата 5.12.2010, 13:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата



**


Профиль
Группа: Участник
Сообщений: 345
Регистрация: 28.11.2010

Репутация: 3
Всего: 5



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

void myfunc(char* buff, int len)
{
    for(int i = 0; i<len; i++){
        analyze(buff[i]);
    }
}

extern stream_init(void (* analyzator)(char*, int));

int main() 
{
    stream_init(&myfunc);
    while(true);
    return 0;
}


так все работает нормально, но мне нужно создать чтото наподобие этого:
Код

class myclass{
public:
    myfunc(char* buff, int len);
};

void myclass::myfunc(char* buff, int len)
{
    for(int i = 0; i<len; i++){
        analyze(buff[i]);
    }
}

extern stream_init(void (* analyzator)(char*, int));

int main() 
{
    myclass newobj;
    stream_init(&newobj.myfunc);
    while(true);
    return 0;
}

PM MAIL   Вверх
Леопольд
Дата 5.12.2010, 14:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 943
Регистрация: 17.6.2009

Репутация: 3
Всего: 13



Код
extern stream_init(void (* analyzator)(char*, int));
Жёстко задаёт сигнатуру. Это указатель на функцию или static метод класса.
Вызов нестатического метода класса треbует указатель на инстанс. Этот указатель надо как-то передать. Как это сделать в многопоточном приложении, не знаю. Если однопоточное, то, остаётся вариант с глоbальной переменной.



Это сообщение отредактировал(а) Леопольд - 5.12.2010, 14:28


--------------------
вопросов больше чем ответов
PM MAIL   Вверх
asmdzen
Дата 5.12.2010, 14:51 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата



**


Профиль
Группа: Участник
Сообщений: 345
Регистрация: 28.11.2010

Репутация: 3
Всего: 5



Леопольд, в обшем мне нужно чтоб функция обрабатывалась как обьект, тоесть если имеем:

Код

void myfunc()
{
    static int x = 0;
    if(!x) x++;
}


то нужно скопировать эту функцию в новое место, изменить значение 'x' и передать указатель на функцию создателю потока. Тоесть я просто могу посчитать размер функции после компиляции, вызвать malloc(sizeof(myfunc)) (знаю что это не должно сработать), потом memcpy и после просто по адрессу 'x' изменить 0 на нужное значение. Но насколько я понимаю static int x это просто глобальная переменная которая будет видна только из myfunc(), а хотелось чтоб она была бы прямо в коде ) 

Возможно ли в с++ такое обращение с функциями?
PM MAIL   Вверх
Леопольд
Дата 5.12.2010, 15:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 943
Регистрация: 17.6.2009

Репутация: 3
Всего: 13



Цитата(asmdzen @  5.12.2010,  14:51 Найти цитируемый пост)
то нужно скопировать эту функцию в новое место, изменить значение 'x' и передать указатель на функцию создателю потока.
Код
template<std::size_t x>
void myfunc()
{
}

//...
//&myfunc<0> != &myfunc<1>




--------------------
вопросов больше чем ответов
PM MAIL   Вверх
asmdzen
Дата 5.12.2010, 15:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата



**


Профиль
Группа: Участник
Сообщений: 345
Регистрация: 28.11.2010

Репутация: 3
Всего: 5



Леопольд,  это хороший пример работы с шаблонами )
но этот код не позволяет сделать что-то наподобие этого:
Код

&myfunc<myvar>

проблема именно в том чтоб можно было передавать шаблону переменные, которые он категорически отказывается принимать (
PM MAIL   Вверх
Леопольд
Дата 5.12.2010, 15:26 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 943
Регистрация: 17.6.2009

Репутация: 3
Всего: 13



Значит надо оbходиться теми, которые он принимает:
http://codepad.org/Kvel9b35
Код
enum ID { id0 = 0, id1, id2 };

static std::string array[id2+1] = {"str0", "str1", "str2"};

template<ID id>
void foo()
{
    std::cout << array[id] << std::endl;
}

int main()
{
    foo<id0>();
    foo<id1>();
    foo<id2>();

    return 0;
}



--------------------
вопросов больше чем ответов
PM MAIL   Вверх
asmdzen
Дата 5.12.2010, 16:07 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата



**


Профиль
Группа: Участник
Сообщений: 345
Регистрация: 28.11.2010

Репутация: 3
Всего: 5



Леопольд, спасибо, это сойдет, не для общего случая, но в моем случае могут быть не более 4 обьектов, просто было интересно реализовать чтото подобное в runtime'e )
PM MAIL   Вверх
Леопольд
Дата 6.12.2010, 06:34 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 943
Регистрация: 17.6.2009

Репутация: 3
Всего: 13



Цитата(asmdzen @  5.12.2010,  16:07 Найти цитируемый пост)
Леопольд, спасибо, это сойдет, не для общего случая
Для общего лучше использовать boost::thread, если текущий стандарт С++, в будущем стандарте std::thread или std::async.
Вот небольшой пример:
Код
#include <iostream>
#include <future>

char const* newThread(char const* str)
{
   std::cout << str << std::endl;
   return "success";
}

int main()
{
   std::future<char const*> tr = std::async(std::launch::async, newThread, "run asyncronously");
   
   // tr.get() or tr.wait() makes the main thread to wait
   std::cout << tr.get() << std::endl;
}



Это сообщение отредактировал(а) Леопольд - 6.12.2010, 06:35


--------------------
вопросов больше чем ответов
PM MAIL   Вверх
xvr
Дата 6.12.2010, 12:10 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 7046
Регистрация: 28.8.2007
Где: Дублин, Ирландия

Репутация: 35
Всего: 223



  •  Что бы в функцию потока передать то, что туда передать нельзя, нужно внедрить 'это' в саму функцию.
  •  Для внедрения чего либо в функцию статически используются template'ы
  •  Для передачи вашей информации через параметры template'ов, эта информация должна быть константной
  •  Отсюда следует, что если вы собираетесь передавать this от объекта в функцию, то этот this должен быть константой
  •  Отсюда следует, что ваш объект должен быть статическим

Код

template<class I, I* i>
void func()
{
 i->another_func();
}

struct A {
 void another_func() {;}
};

A a;

main()
{
 func<A,&a>();
}
Так устроит?


PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "C/C++: Для новичков"
JackYF
bsa

Запрещается!

1. Публиковать ссылки на вскрытые компоненты

2. Обсуждать взлом компонентов и делиться вскрытыми компонентами

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


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, JackYF, bsa.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Для новичков | Следующая тема »


 




[ Время генерации скрипта: 0.0539 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.