Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск  
 
 
Рейтинг 4.69/13: Рейтинг темы: голосов - 13, средняя оценка - 4.69
 Аватар для bedvit
1210 / 261 / 22
Регистрация: 20.05.2016
Сообщений: 1,147
Записей в блоге: 22

Потокобезопасные переменные в функции

15.03.2021, 12:23. Показов 3166. Ответов 46
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Мое почтение, джентльмены.
Функция "AutoWrapX" вызывается из разных потоков, будут ли потокобезопасны следующие переменные? (в комментариях мои предположения):
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
HRESULT AutoWrapX(int autoType, CComVariant* pvResult, CComVariant* pDisp, bool messageErrOff, const wchar_t* ptName, int cArgs...)
{
    HRESULT hr = S_FALSE; //Да
    IDispatch* pDispNew = pDisp->pdispVal; //Да
    CComVariant pvResultLoc; //?
    size_t ptNameSize = wcslen(ptName); //Да
    std::wstring s(ptName); //?
    wchar_t* ptNameBuf = &s[0]; //?
    std::vector <CComVariant> param; //?
    DISPPARAMS dp = { NULL, NULL, 0, 0 };//struct{}// ?
...
    va_list marker;// Да
    va_start(marker, cArgs);
    for (int i = 0; i < cArgs; i++) { param.insert(param.begin(), va_arg(marker, VARIANT)); }// Extract arguments...//?
    va_end(marker);
}
Благодарю за ответы.
0
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
15.03.2021, 12:23
Ответы с готовыми решениями:

Переменные,значение функции,вспомогательные переменные.
1)Даны переменные A,B,C.Изменить их значения,переместив их содержимое из A-в B,B-в C,C-в A,и вывести новые значения переменных A,B,C. ...

Потокобезопасные классы для запросов к серверу SQL из VB.NET приложения
Сижу и собственно впервые пишу многопоточный сервер с запросами к БД MS SQL. До этого как то всё десктопные приложения. Потому, чтобы...

Как будут инициализированы переменные в теле функции и вне тела функции?
Здравствуйте. Подскажите, пожалуйста, как будут инициализированы переменные в теле функции и вне тела функции? Какими значениями? ...

46
 Аватар для bedvit
1210 / 261 / 22
Регистрация: 20.05.2016
Сообщений: 1,147
Записей в блоге: 22
23.03.2021, 18:04  [ТС]
Студворк — интернет-сервис помощи студентам
Цитата Сообщение от bedvit Посмотреть сообщение
std::unique_ptr<XLOPER12, decltype(&xlAutoFree12X)>uPtr1(new XLOPER12{ 0, 0}, &xlAutoFree12X);
XLOPER12* pxRtnValue = uPtr1.get();
Можно ли сделать запись короче, не используя переменную "uPtr1"?
Что-то вроде такой (так не работает)
C++
1
2
3
4
5
//было
std::unique_ptr<XLOPER12, decltype(&xlAutoFree12X)>uPtr1(new XLOPER12{ 0, 0}, &xlAutoFree12X);
XLOPER12* pxRtnValue = uPtr1.get();
//хотелось бы
XLOPER12* pxRtnValue = (std::unique_ptr<XLOPER12, decltype(&xlAutoFree12X)>(new XLOPER12{ 0, 0}, &xlAutoFree12X)).get()
0
19501 / 10106 / 2461
Регистрация: 30.01.2014
Сообщений: 17,825
23.03.2021, 19:19
bedvit, а что это должно означать? В первом варианте - понятно: создается динамический ресурс, время жизни которого контролирует умный указатель, как минимум до конца области видимости. А что ваш желаемый вариант делает - не понятно.
0
 Аватар для bedvit
1210 / 261 / 22
Регистрация: 20.05.2016
Сообщений: 1,147
Записей в блоге: 22
24.03.2021, 09:42  [ТС]
DrOffset, хотел сделать по функционалу тоже самое, но короче .
Вот так работает:
C++
1
2
MessageBox(0, L"Hello Word", 0, MB_OK | MB_ICONINFORMATION); //ОК
MessageBox(0, std::wstring(L"Hello Word").c_str(), 0, MB_OK | MB_ICONINFORMATION); //ОК
а так - нет
C++
1
2
3
4
std::wstring wStr(L"Hello Word");
const wchar_t* msg1 = wStr.c_str(); //ОК
 
const wchar_t* msg2 = std::wstring(L"Hello Word").c_str(); //err
В чем причина?
0
фрилансер
 Аватар для Алексей1153
6495 / 5723 / 1133
Регистрация: 11.10.2019
Сообщений: 15,284
24.03.2021, 10:45
Цитата Сообщение от bedvit Посмотреть сообщение
MessageBox(0, std::wstring(L"Hello Word").c_str(),
объект временный, но он будет жить до выхода из функции MessageBox. Поэтому указатель, полученный из c_str() - тоже. Ок

Цитата Сообщение от bedvit Посмотреть сообщение
std::wstring wStr(L"Hello Word");
const wchar_t* msg1 = wStr.c_str(); //ОК
объект на стеке, но использование указателя - до его (объекта) разрушения. Ок

Цитата Сообщение от bedvit Посмотреть сообщение
const wchar_t* msg2 = std::wstring(L"Hello Word").c_str(); //err
объект временный. Будет уничтожен, если не ошибаюсь, сразу после выполнения оператора =
В любом случае - на следующей строке кода объект уже разрушен, а висячая ссылка осталась
1
 Аватар для bedvit
1210 / 261 / 22
Регистрация: 20.05.2016
Сообщений: 1,147
Записей в блоге: 22
24.03.2021, 11:03  [ТС]
Цитата Сообщение от Алексей1153 Посмотреть сообщение
будет жить до выхода из функции MessageBox.
а здесь
Цитата Сообщение от Алексей1153 Посмотреть сообщение
на следующей строке кода объект уже разрушен
Ведь тоже в функции объявляется, почему в первом случае не разрушается, а во втором разрушается?
0
фрилансер
 Аватар для Алексей1153
6495 / 5723 / 1133
Регистрация: 11.10.2019
Сообщений: 15,284
24.03.2021, 11:18
bedvit, в случае с MessageBox:

MessageBox(0, std::wstring(L"Hello Word").c_str(),

компилятор создаёт безымянный объект std::wstring, инициализирует. У объекта вызывается метод, возвращающий его внутренний указатель

но все эти объекты будут живы, потому что они используются в качестве аргументов при вызове MessageBox. Их "область видимости" и жизнь ограничена круглыми скобками MessageBox
-------------------
а во втором случае вызов operator=(.............) - с таким же поведением

Добавлено через 2 минуты
вообще, при любых сомнениях можно не рисковать и расписать так, чтобы не было неоднозначностей с точки зрения читаемости. При этом всё автоматически "сделается правильно". Быстродействие это не ухудшит, так как всё равно всё то же самое будет происходить
1
 Аватар для bedvit
1210 / 261 / 22
Регистрация: 20.05.2016
Сообщений: 1,147
Записей в блоге: 22
24.03.2021, 11:21  [ТС]
Алексей1153, ясно.
Цитата Сообщение от DrOffset Посмотреть сообщение
А что ваш желаемый вариант делает - не понятно.
Вышеописанные примеры, к тому, что я хотел сделать безымянный объект std::unique_ptr и вызвать его метод, но не вышло по незнанию, или в принципе невозможно (время жизни до конца работы функции)?
0
фрилансер
 Аватар для Алексей1153
6495 / 5723 / 1133
Регистрация: 11.10.2019
Сообщений: 15,284
24.03.2021, 11:30
Цитата Сообщение от bedvit Посмотреть сообщение
XLOPER12* pxRtnValue = (std::unique_ptr<XLOPER12, decltype(&xlAutoFree12X)>(new XLOPER12{ 0, 0}, &xlAutoFree12X)).get()

если речь про строку №5 - то XLOPER12* pxRtnValue - висячий указатель

Цитата Сообщение от bedvit Посмотреть сообщение
//было
std::unique_ptr<XLOPER12, decltype(&xlAutoFree12X)>uPtr1(new XLOPER12{ 0, 0}, &xlAutoFree12X);
XLOPER12* pxRtnValue = uPtr1.get();
а так - ОК. Если, конечно, не возвращать pxRtnValue наружу из функции (будет тот же эффект)

если нужно наружу, то нужно и возвращать объект std::unique_ptr

или открепить указатель через release
0
 Аватар для bedvit
1210 / 261 / 22
Регистрация: 20.05.2016
Сообщений: 1,147
Записей в блоге: 22
24.03.2021, 11:59  [ТС]
Поясню, была идея сократить количество переменных. Потому, как мне нужен указатель (XLOPER12*), а остальное это промежуточные переменные (не используемые дальше), т.е. для каждого указателя не заводить три переменные.
Вместо трех: "uPtr1", "uPtr1"(get) и "pxRtnValue"
C++
1
2
std::unique_ptr<XLOPER12, decltype(&xlAutoFree12X)>uPtr1(new XLOPER12{ 0, 0}, &xlAutoFree12X);
XLOPER12* pxRtnValue = uPtr1.get();
сделать одну: "pxRtnValue"
C++
1
XLOPER12* pxRtnValue = (std::unique_ptr<XLOPER12, decltype(&xlAutoFree12X)>(new XLOPER12{ 0, 0}, &xlAutoFree12X)).get()
Но фокус не удался :)
0
фрилансер
 Аватар для Алексей1153
6495 / 5723 / 1133
Регистрация: 11.10.2019
Сообщений: 15,284
24.03.2021, 12:12
bedvit, а зачем тогда std::unique_ptr ? Для чего всё это. Ведь именно объект std::unique_ptr автоматизирует управление памятью, которую оборачивает

на мой взгляд тут некоторое переусложнение. А по такому пути не проще?

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
struct XLOPER12
{
      int* p{};//тут какие-то динамические данные
 
     XLOPER12(int,int)
     {
     }
 
     ~XLOPER12()
     {
             delete /*[]*/ p;//тут они удаляются
     }
};
 
auto CreatePtr()
{
    return std::make_unique(0, 0);
}
0
19501 / 10106 / 2461
Регистрация: 30.01.2014
Сообщений: 17,825
24.03.2021, 12:21
Цитата Сообщение от bedvit Посмотреть сообщение
хотел сделать по функционалу тоже самое, но короче
Когда вы делаете короче, то "по функционалу то же самое" никак не получится.

Цитата Сообщение от bedvit Посмотреть сообщение
была идея сократить количество переменных. Потому, как мне нужен указатель (XLOPER12*), а остальное это промежуточные переменные (не используемые дальше), т.е. для каждого указателя не заводить три переменные.
Вот имено что не "промежуточные" и очень даже используемые дальше. Умный указатель контролирует время жизни вашего ресурса до конца области видимости, в этом его предназначение и "функционал". Когда вы переписываете код - вы меняете функционал, а не просто сокращаете запись.

Это у меня такое ощущение, или на самом деле у вас нет четкого понимания что каждая из этих строк делает в программе?
0
 Аватар для bedvit
1210 / 261 / 22
Регистрация: 20.05.2016
Сообщений: 1,147
Записей в блоге: 22
24.03.2021, 12:28  [ТС]
Цитата Сообщение от Алексей1153 Посмотреть сообщение
зачем тогда std::unique_ptr ?
именно для управление памятью. Все верно.
XLOPER12 эта структура от microsoft (я ее не смогу изменить), некоторые я сам создаю, некоторые получаю.

Если интересно, вот как она выглядит:
Кликните здесь для просмотра всего текста
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
typedef struct xloper12
{
    union
    {
        double num;                     /* xltypeNum */
        XCHAR *str;                     /* xltypeStr */
        BOOL xbool;                     /* xltypeBool */
        int err;                        /* xltypeErr */
        int w;
        struct
        {
            WORD count;                 /* always = 1 */
            XLREF12 ref;
        } sref;                     /* xltypeSRef */
        struct
        {
            XLMREF12 *lpmref;
            IDSHEET idSheet;
        } mref;                     /* xltypeRef */
        struct
        {
            struct xloper12 *lparray;
            RW rows;
            COL columns;
        } array;                    /* xltypeMulti */
        struct
        {
            union
            {
                int level;          /* xlflowRestart */
                int tbctrl;         /* xlflowPause */
                IDSHEET idSheet;        /* xlflowGoto */
            } valflow;
            RW rw;                      /* xlflowGoto */
            COL col;                    /* xlflowGoto */
            BYTE xlflow;
        } flow;                     /* xltypeFlow */
        struct
        {
            union
            {
                BYTE *lpbData;          /* data passed to XL */
                HANDLE hdata;           /* data returned from XL */
            } h;
            long cbData;
        } bigdata;                  /* xltypeBigData */
    } val;
    DWORD xltype;
} XLOPER12, *LPXLOPER12;


Добавлено через 6 минут
Цитата Сообщение от DrOffset Посмотреть сообщение
Когда вы делаете короче, то "по функционалу то же самое" никак не получится.
Пример (функционал одинаков):
C++
1
2
3
4
5
6
7
8
9
10
11
//с 2мя переменными
std::wstring wStr(L"Hello Word");
const wchar_t* msg1 = wStr.c_str();
MessageBox(0, msg1 , 0, MB_OK | MB_ICONINFORMATION);
 
//или так, с 1й переменной (короче)
std::wstring wStr(L"Hello Word");
MessageBox(0, wStr.c_str(), 0, MB_OK | MB_ICONINFORMATION);
 
//без переменной (еще короче)
MessageBox(0, std::wstring(L"Hello Word").c_str(), 0, MB_OK | MB_ICONINFORMATION);
0
19501 / 10106 / 2461
Регистрация: 30.01.2014
Сообщений: 17,825
24.03.2021, 12:31
Цитата Сообщение от Алексей1153 Посмотреть сообщение
Их "область видимости" и жизнь ограничена круглыми скобками MessageBox
Она ограничена, грубо говоря, текущим выражением. Жить такой объект будет до конца выражения, т.е. до условных точки с запятой.

Поэтому вот такой код, например, будет корректен:
C++
1
2
3
4
5
6
7
8
9
char const * test(char const * s) 
{
     return s;
}
//............
 
std::cout << test(std::string("test string").c_str()); 
// время жизни std::string("test string") НЕ ограничено скобками вызова функции test(), 
// поэтому std::cout получит валидный указатель
Добавлено через 2 минуты
Цитата Сообщение от bedvit Посмотреть сообщение
Пример (функционал одинаков):
Вы выше показывали совсем другой пример. Я о нем говорю.
1
фрилансер
 Аватар для Алексей1153
6495 / 5723 / 1133
Регистрация: 11.10.2019
Сообщений: 15,284
24.03.2021, 12:31
bedvit, тогда можно обернуть

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
struct myXLOPER12
{
     XLOPER12 value{};
 
     myXLOPER12(int,int)
     {
            //инициализация value
     }
 
     ~myXLOPER12()
     {
             //вызов функций очистки
     }
};
0
19501 / 10106 / 2461
Регистрация: 30.01.2014
Сообщений: 17,825
24.03.2021, 12:31
---
0
 Аватар для bedvit
1210 / 261 / 22
Регистрация: 20.05.2016
Сообщений: 1,147
Записей в блоге: 22
24.03.2021, 12:38  [ТС]
Цитата Сообщение от DrOffset Посмотреть сообщение
Я о нем говорю.
Я понял, я показал, пример, на котором хотел получить аналогию, того, как это можо сделать со строкой. Понятно, что код в примере разного функционала, т.к. в этом и был вопрос (одинаковый функционал с сокращением количества переменных). Но я так понял этого нельзя сделать в принципе (создать безымянный умный указатель и его использовать).
Цитата Сообщение от Алексей1153 Посмотреть сообщение
можно обернуть
для создаваемых мною да, а что делать с такими структурами, которые приходят ко мне извне?
0
фрилансер
 Аватар для Алексей1153
6495 / 5723 / 1133
Регистрация: 11.10.2019
Сообщений: 15,284
24.03.2021, 12:42
Цитата Сообщение от bedvit Посмотреть сообщение
которые приходят ко мне извне
ну так их заголовочник/определение же имеется? Или нет?
0
19501 / 10106 / 2461
Регистрация: 30.01.2014
Сообщений: 17,825
24.03.2021, 12:43
Цитата Сообщение от bedvit Посмотреть сообщение
Но я так понял этого нельзя сделать в принципе (создать безымянный умный указатель и его использовать).
Можно конечно. Но весь вопрос в контексте. Так, как вы показали - нельзя (причем нельзя именно в вашем контексте, а не вообще). Именно поэтому я спрашиваю про понимание того, что происходит.

Вызывать uPtr1.get() по типу вашего вызова wStr.c_str() в нужных местах, вместо создания отдельного pxRtnValue вполне аналогично вашему примеру со строками.
0
 Аватар для bedvit
1210 / 261 / 22
Регистрация: 20.05.2016
Сообщений: 1,147
Записей в блоге: 22
24.03.2021, 13:19  [ТС]
Цитата Сообщение от Алексей1153 Посмотреть сообщение
заголовочник/определение же имеется
Имеется
Цитата Сообщение от DrOffset Посмотреть сообщение
Вызывать uPtr1.get()
Возможен и такой вариант. Здесь вопрос как целесообразней: Создать 3 переменных, или изменить часть кода на uPtr1.get() (не относится к вопросу, сфера персонального выбора)
0
264 / 153 / 33
Регистрация: 29.06.2019
Сообщений: 1,549
24.03.2021, 17:34
Цитата Сообщение от DrOffset Посмотреть сообщение
Вызывать uPtr1.get() .. в нужных местах
вообще мне встречалась мысль и я с ней согласна, что доставать ptr из обёртки смарт-пойнтера (в частности unique_ptr), в частности через get(), - глупо, т.к. тогда не понятно зачем использовать вообще эту обёртку, если доставая из неё мы сами же и избавляемся от её защитного предназначения... имхо
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
24.03.2021, 17:34

Пропадают локальные переменные функции после первого запуска функции
Я написал код для расчёта электрического кольца. Я постепенно упрощаю схему параллельными и последовательными операциями. Вот мой код: (...

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

Переменные в функции
Здравствуйте, имеется сайт на Wordpress. Улучшаю его, допиливаю. (Чтобы исполнялся php код на страницах юзаю плагин Exec-PHP). Столкнулся...

Переменные функции
Как определить, может ли функция php вызвана через переменную?

функции и переменные
void *fun(void *b) { vector&lt;int&gt;c (*(vector&lt;int&gt;*)b); for (int i = 7; i &lt; 12; i++) { c.push_back(i); } return 0; ...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
40
Ответ Создать тему
Новые блоги и статьи
Где деньги лежат
kumehtar 02.07.2026
Это - японская подводная лодка I-52 (тип C2, кодовое имя Momi) вышла из Японии в марте 1944 года с миссией в оккупированную немцами Францию (Лорьян). Это была одна из «Янаги»-миссий по обмену. . .
Krabik для WoW 3.3.5a, многоязычный
AmbA 02.07.2026
Допилил бота, думаю что окончательно. Изменения: - добавлена многоязычность - добавлено снятие скриншотов - добавлено поддержание бафов хождения по воде (для жреца, дк и шамана) - и так, по. . .
Алиса нашла кучу ошибок компиляции и запуска в проекте, который без проблем компилировался и запускался)))
anaschu 30.06.2026
Я пока посмеюся, но завтра проверю. А вообще интерсно. Дал алисе файл, в котором точно нет ошибок компиляции и запуска, и попросил их найти. Нашла кучу))) Критические ошибки, мешающие компиляции и. . .
сукцессия 16. Общий обзор, в основном что бы другие ии поняли
anaschu 29.06.2026
# Передаточный документ: модель микоризной сукцессии (для нового чата) Этот документ предназначен для того, чтобы новый чат Claude мог продолжить работу без необходимости заново разбираться в. . .
сукцессия 15 неявная схема
anaschu 29.06.2026
Алиса Калибровка параметров симбиотической модели: технический обзор Содержание: Введение Постановка проблемы Технические аспекты реализации Процесс внедрения изменений
сукцессия 14. Обновленная схема модели
anaschu 28.06.2026
ГЛОБАЛЬНАЯ ОПИСАТЕЛЬНАЯ СПЕЦИФИКАЦИЯ ЭКОСИСТЕМНОЙ МОДЕЛИ «SOIL CHEMISTRY & MYCORRHIZA 2. 0» https:/ / ibb. co/ NnkGpfMd Представленная интегрированная схема описывает непрерывную нелинейную. . .
сукцессия 13. Питон модель трехзонного мицелия, пока что в основном арбускулярного
anaschu 28.06.2026
## Разработка агентной модели микоризной сукцессии: от выявления артефактов к созданию комплексной системы ### Аннотация Представлено исследование по разработке агентной модели микоризной. . .
сукцессия 12. краткий список проверок модели перед запуском.
anaschu 27.06.2026
Скрытые отказы в моделях систем динамики (SD-models) экологических систем: два случая из практики Контекст Разбирался прототип модели систем динамики (SD-модели) микоризной сукцессии: пять. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru