Error this was not captured for this lambda function

error at

RRS feed

  • Remove From My Forums
  • Question

  • std::unique_lock<std::mutex> lk(mut);
    data_cond.wait(lk, []{return !data_queue.empty();});

    error at

    data_cond.wait(lk, []{return !data_queue.empty();});

    ‘this’ was not captured for this lambda function

    where std::condition_variable data_cond;  std::queue<T> data_queue;


    Sigma : Every day has new and fresh idea and then search whether exists,

Answers

    • Marked as answer by
      沈世鈞
      Friday, November 4, 2011 8:57 AM

All replies

  • Seems pretty clear — data_queue is a member of a class/struct object.   The lambda needs to know which object to operate on, however you didn’t tell it, and you didn’t allow it to capture the implicit this needed to access data_queue.  You
    can add a capture clause letting the compiler know you want to capture it though like

    // Disclaimer, I do Windows CE development, which doesn't 
    // have Lambda support yet, so I am doing this from memory
    // I might have the syntax wrong
    data_cond.wait(lk, [this]{return !data_queue.empty();});
    

    Of course, you need to make absolutely certain that your object will outlive the lambda in this case.

  • after tried, invalid type argument it’s my first time to see this kind of writing, [this]{} what does this mean?


    Sigma : Every day has new and fresh idea and then search whether exists,

  • It means you want the lambda to capture the «this» pointer. 
    Here is an example that might help.

    If you are unfamiliar with the concept of the «this» pointer, it is a pointer to the object whose member function you are calling.  For example,

    class Foo
    {
      public:
        int x;
        void function()
        {
            x = 3;          // these lines do the same thing
            this->x = 3; //
        }
    };
    

    A «this» pointer is available to every member function.  It is almost like it is an implicit first parameter passed to every member function.

    Foo f;

    f.function();  // how you normally call an object’s member function

    In an alternate language that didn’t have implicit «this» pointers, you might instead define things like:

    class Foo
    {
      public:
        int x;
        void function(Foo * const the_this_pointer)
        {
            the_this_pointer->x = 3;
        }
    };
    

    And call them like this:

    function(f);

  • why invalid argument , data_cond.wait(lk, [this]{return !data_queue.empty();});?


    Sigma : Every day has new and fresh idea and then search whether exists,

    • Marked as answer by
      沈世鈞
      Friday, November 4, 2011 8:57 AM

    msm.ru

    Нравится ресурс?

    Помоги проекту!

    >
    ‘this’ was not captured for this lambda function

    • Подписаться на тему
    • Сообщить другу
    • Скачать/распечатать тему



    Сообщ.
    #1

    ,
    04.06.10, 12:59

      Код такой:

      ExpandedWrap disabled

        void BitOStream::WriteString(std::string str)

        {

            for_each(str.begin(), str.end(), [](char c)

            {

                WriteByte(c);

            }

            );

        }

      Компилятор(g++ 4.5) выдает:

      ExpandedWrap disabled

        BitOStream.cpp: In lambda function:

        BitOStream.cpp:45:3: ошибка: ‘this’ was not captured for this lambda function

        make: *** [flactrim] Ошибка 1

      WriteByte это приватный метод того же класса:

      ExpandedWrap disabled

        void WriteByte(uint8_t byte, unsigned short bitCount = BITSINBYTE);

      Как исправить ошибку?


      Flex Ferrum



      Сообщ.
      #2

      ,
      04.06.10, 13:01

        Цитата miksayer @ 04.06.10, 12:59

        void BitOStream::WriteString(std::string str) { for_each(str.begin(), str.end(), [this](char c) { WriteByte©; } ); }

        и твой код будет мягким и шелковистым.


        miksayer



        Сообщ.
        #3

        ,
        04.06.10, 13:04

          Цитата Flex Ferrum @ 04.06.10, 13:01

          и твой код будет мягким и шелковистым.

          спасибо
          хочу еще посоветоваться. Что лучше в этом случае использовать: лямбда-выражение, как сделано выше или определить еще один вариант функции WriteByte, чтобы она могла принимала char и передавать уже ее?

          Добавлено 04.06.10, 13:05
          и, кстати, зачем здесь указывать this в квадратных скобках? т.е. мы говорим компилятору, что мы планируем работать с this в самом выражении?


          Flex Ferrum



          Сообщ.
          #4

          ,
          04.06.10, 13:11

            Цитата miksayer @ 04.06.10, 13:04

            и, кстати, зачем здесь указывать this в квадратных скобках? т.е. мы говорим компилятору, что мы планируем работать с this в самом выражении?

            В квадратных скобках указывается т. н. «capture-list» — перечень переменных, видимых в контексте определения лямбда-функции, который должен быть доступен в её теле. Ты перечисляешь либо конкретные переменные, либо используешь специальные формы:
            [=] — все переменные будут доступны по значению.
            [&] — все переменные будут доступны по ссылке.
            Если оставляешь пустым, то из контекста определения ничего не будет «захвачено».


            miksayer



            Сообщ.
            #5

            ,
            07.06.10, 21:26

              спасибо

              0 пользователей читают эту тему (0 гостей и 0 скрытых пользователей)

              0 пользователей:

              • Предыдущая тема
              • C/C++: Общие вопросы
              • Следующая тема

              Рейтинг@Mail.ru

              [ Script execution time: 0,0336 ]   [ 16 queries used ]   [ Generated: 9.02.23, 15:29 GMT ]  

              Hi,

              and first, thanks a lot for this amazing piece of code :-)

              When I try to build my app including the v8pp ‘class’ headers, I get the following error.
              Would you have any idea about what’s happening ?

              Thanks in advance.

              compile output:
              g++ -c -m64 -pipe -g -w -std=c++11 -I../../3rdparty/desktop/include/v8 -Isrc -o build/desktop/obj/javascriptTest.o src/javascriptTest.cpp
              
              In file included from src/javascriptTest.cpp:21:0:
              ../../main/src/javascript/v8pp/class.hpp: In instantiation of ‘v8pp::detail::class_singleton<T>::class_singleton(v8::Isolate*, v8pp::detail::class_info::type_index) [with T = Point; v8pp::detail::class_info::type_index = unsigned int]::<lambda(const v8::FunctionCallbackInfo<v8::Value>&)>’:
              ../../main/src/javascript/v8pp/class.hpp:178:5:   required from ‘struct v8pp::detail::class_singleton<T>::class_singleton(v8::Isolate*, v8pp::detail::class_info::type_index) [with T = Point; v8pp::detail::class_info::type_index = unsigned int]::<lambda(const class v8::FunctionCallbackInfo<v8::Value>&)>’
              ../../main/src/javascript/v8pp/class.hpp:189:5:   required from ‘v8pp::detail::class_singleton<T>::class_singleton(v8::Isolate*, v8pp::detail::class_info::type_index) [with T = Point; v8pp::detail::class_info::type_index = unsigned int]’
              ../../main/src/javascript/v8pp/class.hpp:261:4:   required from ‘static v8pp::detail::class_singleton<T>& v8pp::detail::class_singleton<T>::instance(v8::Isolate*) [with T = Point; v8pp::detail::class_singleton<T> = v8pp::detail::class_singleton<Point>]’
              ../../main/src/javascript/v8pp/class.hpp:369:56:   required from ‘v8pp::class_<T>::class_(v8::Isolate*) [with T = Point]’
              src/javascriptTest.cpp:71:42:   required from here
              ../../main/src/javascript/v8pp/class.hpp:183:74: error: ‘this’ was not captured for this lambda function
              ../../main/src/javascript/v8pp/class.hpp:183:74: error: return-statement with a value, in function returning 'void' [-fpermissive]
              make: *** [build/desktop/obj/javascriptTest.o] Error 1
              
              details:
              • file included from src/javascriptTest.cpp:21:0 being: v8pp/class.hpp
              • src/javascriptTest.cpp:71:42: required from here being
              v8pp::class_<Point> point_class(isolate);
              

              (with Point being a basic int 2d-coord(x,y) class, no template or anything else)

              my environment:
              g++ (Debian 4.7.2-5) 4.7.2
              #define V8_MAJOR_VERSION 4
              #define V8_MINOR_VERSION 5
              #define V8_BUILD_NUMBER 103
              #define V8_PATCH_LEVEL 30
              
              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
              50
              51
              52
              53
              54
              55
              56
              57
              58
              59
              60
              61
              62
              63
              64
              65
              66
              67
              68
              69
              70
              71
              72
              73
              74
              75
              76
              77
              78
              79
              80
              81
              82
              83
              84
              85
              86
              87
              88
              89
              90
              91
              92
              93
              94
              95
              96
              97
              98
              99
              100
              101
              102
              103
              104
              105
              106
              107
              108
              109
              110
              111
              112
              113
              114
              115
              116
              117
              118
              119
              120
              121
              122
              123
              124
              125
              126
              127
              128
              129
              130
              131
              132
              133
              134
              135
              136
              137
              138
              139
              140
              141
              142
              143
              144
              145
              146
              147
              148
              149
              150
              151
              152
              153
              154
              155
              156
              157
              158
              159
              160
              161
              162
              163
              164
              165
              166
              167
              168
              169
              170
              171
              172
              173
              174
              175
              176
              177
              178
              179
              180
              181
              182
              183
              184
              185
              186
              187
              188
              189
              190
              191
              192
              193
              194
              195
              196
              197
              198
              199
              200
              201
              202
              203
              204
              205
              206
              207
              208
              209
              210
              211
              212
              213
              214
              215
              216
              217
              218
              219
              220
              221
              222
              223
              224
              225
              226
              227
              228
              229
              230
              231
              232
              233
              234
              235
              236
              237
              238
              239
              240
              241
              242
              243
              244
              245
              246
              247
              248
              249
              250
              251
              252
              253
              254
              255
              256
              257
              258
              259
              260
              261
              262
              263
              264
              265
              266
              267
              268
              269
              270
              271
              272
              273
              274
              275
              276
              277
              278
              279
              280
              281
              282
              283
              284
              285
              286
              287
              288
              289
              290
              291
              292
              293
              294
              295
              296
              297
              298
              299
              300
              301
              302
              303
              304
              305
              306
              307
              308
              309
              310
              311
              312
              313
              314
              315
              316
              317
              318
              319
              320
              321
              322
              323
              324
              325
              326
              327
              328
              329
              330
              331
              332
              333
              334
              335
              336
              337
              338
              339
              340
              341
              342
              343
              344
              345
              346
              347
              348
              349
              350
              351
              352
              353
              354
              355
              356
              357
              358
              359
              360
              361
              362
              363
              364
              365
              366
              367
              368
              369
              370
              371
              372
              373
              374
              375
              376
              377
              378
              379
              380
              381
              382
              383
              384
              385
              386
              387
              388
              389
              390
              391
              392
              393
              394
              395
              396
              397
              398
              399
              400
              401
              402
              403
              404
              405
              406
              407
              408
              409
              410
              411
              412
              413
              414
              415
              416
              417
              418
              419
              420
              421
              422
              423
              424
              425
              426
              427
              428
              429
              430
              431
              432
              433
              434
              435
              436
              437
              438
              439
              440
              441
              442
              443
              444
              445
              446
              447
              448
              449
              450
              451
              452
              453
              454
              455
              456
              457
              458
              459
              460
              461
              462
              463
              464
              465
              466
              467
              468
              469
              470
              471
              472
              473
              474
              475
              476
              477
              478
              479
              480
              481
              482
              483
              484
              485
              486
              487
              488
              489
              490
              491
              492
              493
              494
              495
              496
              497
              498
              499
              500
              501
              502
              503
              504
              505
              506
              507
              508
              509
              510
              511
              512
              513
              514
              515
              516
              517
              518
              519
              520
              521
              522
              523
              524
              525
              526
              527
              528
              529
              530
              531
              532
              533
              534
              535
              536
              537
              538
              539
              540
              541
              542
              543
              544
              
              #include <iostream>
              #include <ctime>
              #include <vector>
              #include <windows.h>
              #include <sstream>
              #include <iomanip>
              #include <cmath>
              #include <algorithm>
              #include <string>
              #include <list>
              #include <cctype>
              using namespace std;
              void ClearScreen();
              class Game;
              class Item;
              class Character {
              public:
              double accuraty;
              double agility;
              double endurance;
              int hitpoints;
              int experience;
              int level;
              int freeskills;
              int money;
              double speed;
              double strength;
              int distance;
              vector <Item> inventory;
              string object;
              Character (string o) : object(o)
              {
                  cout << "Создался объект " << object << endl;
              }
              ~Character()
              {
                  cout << "Разрушился объект " << object << " с хр " << hitpoints << endl;
              }
              int checklevel();
              void inventoryShow(Game &);
              void useItem(Character &, int, Game &);
              void useChoiseItem(Game &, Character &);
              void generatecharacter();
              void freeskillsassign();
              };
               
              class Battle;
              class Game {
              public:
              friend class Item;
              void showgamelogs();
              void cleargamelogs();
              void clearmainlogfromtemp();
              string gamelogs;
              string tempgamelogs;
              string gamelogstats;
              vector <string> mainlog;
              vector <string> templog;
              void play(Game &);
              void roadjourney(Battle &, Character &, Character &, Item &, Game &);
              void healing(Character &, double);
              void bardisplay(Character &, Character &, Game &);
              void bardisplay(Character &, Game &);
              void osstostring( std::ostream& s );
              void osstostringtemp(  std::ostream& s );
              void osstostring2( std::ostream& s );
              };
               
              void Game::osstostring( std::ostream& s )
              {
                  gamelogs = dynamic_cast<std::ostringstream&>(s).str();
                  mainlog.push_back(gamelogs);
              }
              void Game::osstostringtemp( std::ostream& s )
              {
                  tempgamelogs = dynamic_cast<std::ostringstream&>(s).str();
                  templog.push_back(tempgamelogs);
              }
              void Game::osstostring2( std::ostream& s )
              {
                  gamelogstats += dynamic_cast<std::ostringstream&>(s).str();
              }
              // int CounterClear = 0;
              // int BarCounter = 0;
              void Game::showgamelogs()
              {
              //    ++CounterClear;
              //    cout << "Число логов: " << CounterClear << "nЧисло баров: " << BarCounter << endl;
                  ClearScreen();
                  if (templog.size() > 0)
                  {
                  for (auto vectorit = mainlog.begin(); vectorit != mainlog.end(); ++vectorit)
                      gamelogs += *vectorit;
                  for (auto vectorit = templog.begin(); vectorit != templog.end(); ++vectorit)
                      tempgamelogs += *vectorit;
                      cout << gamelogstats << gamelogs << tempgamelogs;
                  }
                  else
                  {
                  for (auto vectorit = mainlog.begin(); vectorit != mainlog.end(); ++vectorit)
                      gamelogs += *vectorit;
                      cout << gamelogstats << gamelogs;
                  }
                  tempgamelogs = "";
                  gamelogs = "";
                  gamelogstats = "";
              }
              void Game::cleargamelogs()
              {
                  mainlog.clear();
                  templog.clear();
              }
              void Game::clearmainlogfromtemp()
              {
                  auto pred = [&templog](const std::string& key) ->bool
                  {
                      return std::find(templog.begin(), templog.end(), key) != templog.end();
                  };
                  mainlog.erase(std::remove_if(mainlog.begin(), mainlog.end(), pred), mainlog.end());
              }
              void Game::healing(Character &p, double h)
              {
                  p.hitpoints += h;
                  if (p.hitpoints > 100)
                  p.hitpoints = 100;
               
              }
              int Character::checklevel()
              {
                if (experience >= (250 * (pow(level,(5-1)))))
                {
                level += 1;
                freeskills +=3;
                return 1;
                }
                else
                return 0;
              }
               
              class Battle : public Game {
              private:
              public:
               string object;
               Battle (string o) : object(o)
              {
                  cout << "Создался объект " << object << endl;
              }
               ~Battle()
              {
                  cout << "Разрушился объект " << object << endl;
              }
              void callopponent(Character &, Character &, Item &, Game &);
              void battlelogic(Character &, Character &, Item &, Game &);
              void battledistance(Character &, Character &, Game &);
              void battlehit(Character &, Character &, Game &);
              void battledamage(Character &, Character &, Game &);
              void surrendlogic(Character &, Character &, Game &);
              void opponentTurn(Character &, Character &, Item &, Game &);
              };
              class Item
              {
                  public:
                  string name;
                  string type;
                  double weight;
                  double damage;
                  double healing;
                  friend bool operator==(const Item& lhs, const Item& rhs)
                  {
                      return lhs.name == rhs.name && lhs.type == rhs.type;
                  }
                  void itemDrop(Character &p, Game &game);
                  void itemToThrow(Character &p);
              };
              void Item::itemDrop(Character & p, Game & game)
              {
                  vector<Item> randomitems = {{"Молот","Оружие",10,20,0},{"Топор","Оружие",20,10,0},{"Меч","Оружие",10,30,0}
                  ,{"Маленькое зелье","Зелье",1,0,10},{"Среднее зелье","Зелье",3,0,25},{"Большое зелье","Зелье",5,0,50}};
                  int itemcount = 0;
                  int chance = 0;
                  for (int i = 0; i != 1; ++i)
                  {
                      itemcount = (rand() % 4) + 0;
                      switch (itemcount)
                      {
                      case 0:
                      chance = 50;
                      if((rand() % 100) + 1 > chance)
                      --i;
                      break;
                      case 1:
                      chance = 40;
                      if((rand() % 100) + 1 > chance)
                      --i;
                      break;
                      case 2:
                      chance = 30;
                      if((rand() % 100) + 1 > chance)
                      --i;
                      break;
                      case 3:
                      chance = 20;
                      if((rand() % 100) + 1 > chance)
                      --i;
                      break;
                      }
                  }
                  if (itemcount > 1)
                  {
                  vector <Item> dropoutput;
                  for (int i = 0; i != itemcount; ++i)
                  {
                  int randomIndex = rand() % randomitems.size();
                  if (randomitems[randomIndex].name == "Большое зелье")
                  {
                      chance = 5;
                      if((rand() % 100) + 1 < chance)
                      dropoutput.push_back(randomitems[randomIndex]);
                      else
                      --i;
                      continue;
                  }
                  else if (randomitems[randomIndex].name == "Маленькое зелье")
                  {
                      chance = 25;
                      if((rand() % 100) + 1 < chance)
                      dropoutput.push_back(randomitems[randomIndex]);
                      else
                      --i;
                      continue;
                  }
                  else if (randomitems[randomIndex].name == "Топор")
                  {
                      chance = 5;
                      if((rand() % 100) + 1 < chance)
                      dropoutput.push_back(randomitems[randomIndex]);
                      else
                      --i;
                      continue;
                  }
                  else if (randomitems[randomIndex].name == "Меч")
                  {
                      chance = 5;
                      if((rand() % 100) + 1 < chance)
                      dropoutput.push_back(randomitems[randomIndex]);
                      else
                      --i;
                      continue;
                  }
                  else if (randomitems[randomIndex].name == "Молот")
                  {
                      chance = 5;
                      if((rand() % 100) + 1 < chance)
                      dropoutput.push_back(randomitems[randomIndex]);
                      else
                      --i;
                      continue;
                  }
                  else if (randomitems[randomIndex].name == "Среднее зелье")
                  {
                      chance = 15;
                      if((rand() % 100) + 1 < chance)
                      dropoutput.push_back(randomitems[randomIndex]);
                      else
                      --i;
                      continue;
                  }
                  }
                  game.osstostring(ostringstream().flush() << "После боя вы находите трофеи: " << endl);
                  int ch = 0;
                  do {
                  game.osstostringtemp(ostringstream().flush() << "Выберите вещи по номерами позиций или A, если хотите забрать их" <<
                  " или n, чтобы выйти из боя. " << endl);
                  int c = 1;
                  for (auto vectorit = dropoutput.begin(); vectorit != dropoutput.end(); ++vectorit,++c)
                  {
                      game.osstostringtemp(ostringstream().flush() << c << ". " << (*vectorit).name << endl);
                  }
                  game.showgamelogs();
                  cin >> ch;
                  p.inventory.push_back(dropoutput[(ch - 1)]);
                  dropoutput.erase(dropoutput.begin() + (ch - 1));
                  game.osstostring(ostringstream().flush() << "Вы выбрали " << dropoutput[(ch - 1)].name << endl);
                  } while (ch != 0 && dropoutput.size() > 0);
                  }
                  game.clearmainlogfromtemp();
               
              }
               
               
              void Item::itemToThrow(Character &p)
              {
                  string itemtodrop;
                  cout << "Которую вещь вы хотите бросить?" << endl;
                  getline(cin, itemtodrop);
                  Item temp;
                  for (auto vectorit = p.inventory.begin(); vectorit != p.inventory.end(); ++vectorit)
                  {
                      if ((*vectorit).name == itemtodrop)
                      {
                       temp = {(*vectorit)};
                       break;
                      }
                  }
                  auto it = find(p.inventory.begin(),p.inventory.end(), temp);
                  if(it != p.inventory.end())
                  p.inventory.erase(it);
              }
               
              void Character::inventoryShow(Game &game)
              {
                  int c = 1;
                  for (auto vectorit = inventory.begin(); vectorit != inventory.end(); ++vectorit, ++c)
                  {
                      if ((*vectorit).type == "Оружие")
                      {
                      cout << c << ". " << "Оружие: " << (*vectorit).name;
                      cout << " - Урон: " << (*vectorit).damage << endl;
                      }
               
                      else if ((*vectorit).type == "Зелье")
                      {
                      cout << c << ". " << "Зелье: " << (*vectorit).name;
                      cout << " - Лечельный эффект: " << (*vectorit).healing << endl;
                      }
                  }
              }
               
              void Character::useItem(Character &p, int ich, Game &game)
              {
                  if(inventory[ich].type == "Зелье")
                  {
                      game.healing(p, inventory[ich].healing);
                      p.inventory.erase(inventory.begin() + ich);
                  }
                  else
                  cout << "Test" << endl;
               
              }
               
              void Character::useChoiseItem(Game &game, Character &p)
              {
                  int ich;
                  cout << "Будете что-то использовать/поменять или выйдете? Выберите номер позиции для применения или n для выхода." << endl;
                  cin >> ich;
                  if (ich > 0)
                  {
                      useItem(p,(ich - 1), game);
                      if (inventory[ich - 1].type == "Зелье")
                      game.osstostring(ostringstream().flush() << "Вы вылечились на " << inventory[ich - 1].healing << endl);
                  }
                  else if (ich == 0)
                  {
                      game.osstostringtemp(ostringstream().flush() << "Вы вышли из инвентаря" << endl);
                  }
                  else
                      game.osstostringtemp(ostringstream().flush() << "У вас пустой инвентарь!" << endl);
              }
              void Game::play(Game &game)
              {
                  Character p("Vova");
                  p.inventory.push_back({"Маленькое зелье","Зелье",1,0,10});
                  p.inventory.push_back({"Среднее зелье","Зелье",1,0,25});
                  p.inventory.push_back({"Большое зелье","Зелье",1,0,50});
                  Item i;
                  p.generatecharacter();
                  Battle b("Battle");
                  Character o("Oppo");
                  int ch = 0;
                  while (p.hitpoints > 0)
                  {
                      if (p.freeskills == 0)
                      {
                       cout << "Вы на пути. Что будете делать?n1) Идти дальше.n2) Посмотреть инвентарь.n";
                       cin >> ch;
                       switch (ch)
                       {
                       case 1:
                       roadjourney(b, p, o, i, game);
                       break;
                       case 2:
                       p.inventoryShow(game);
                       p.useChoiseItem(game,p);
                       break;
                       }
                      }
                      else
                      {
                       cout << "Вы на пути. Что будете делать?n1) Идти дальше.n2) Посмотреть инвентарь.n"
                       << "3) Назначить свободное количество очок(" << p.freeskills << ")" << endl;
                       cin >> ch;
                       switch (ch)
                       {
                       case 1:
                       roadjourney(b, p, o, i, game);
                       break;
                       case 2:
                       p.inventoryShow(game);
                       p.useChoiseItem(game,p);
                       break;
                       case 3:
                       p.freeskillsassign();
                       break;
                       }
                      }
                  }
              }
               
              void Game::roadjourney(Battle &b, Character &p, Character &o, Item &i, Game &game)
              {
                  int fate = (rand() % 3) + 1;
                  switch (fate)
                  {
                  case 1:
                      b.callopponent(p, o, i, game);
                      break;
                  case 2:
                      cout << "Вы ходите дальше" << endl;
                      break;
                  case 3:
                      cout << "Вы находите сокровище" << endl;
                      break;
                  }
              }
              void Game::bardisplay(Character &p, Character &o, Game &game)
              {
                  vector <string> pskillnames = {"Сила","Ловкость","Точность","Выносливость","Скорость", "Здоровье"};
                  vector <double> pskillstats = {p.strength,p.agility,p.accuraty,p.endurance,p.speed, p.hitpoints};
                  vector <string> oskillnames = {"Сила","Ловкость","Точность","Выносливость","Скорость", "Здоровье"};
                  vector <double> oskillstats = {o.strength,o.agility,o.accuraty,o.endurance,o.speed, o.hitpoints};
                  if (p.object == "Vova")
              {
                  game.osstostring2(ostringstream().flush() << "Ваши характеристики:                                Характеристики противника: "
                              << endl);
                  for (int n = 0, s = 0, i = 6;s < i;n++, s++)
                      if (pskillstats[n] == 10 && n != 0)
                      {
                       game.osstostring2(ostringstream().flush() << pskillnames[n] << ":t" << pskillstats[n] << setw(51) << oskillnames[n]
                       << ":t" << oskillstats[n] << endl);
                       continue;
                      }
                      else if (pskillstats[n] == p.hitpoints)
                      {
                       game.osstostring2(ostringstream().flush() << pskillnames[n] << ":t" << pskillstats[n] << setw(50) << oskillnames[n] << ":t"
                       << oskillstats[n] << endl);
                       continue;
                      }
                      else if (pskillstats[n] == 10 && n == 0)
                      {
                       game.osstostring2(ostringstream().flush() << pskillnames[n] << ":tt" << pskillstats[n] << setw(51) << oskillnames[n]
                       << ":t" << oskillstats[n] << endl);
                       continue;
                      }
                      else if (pskillnames[n].size() < 6)
                      {
                       game.osstostring2(ostringstream().flush() << pskillnames[n] << ":tt" << pskillstats[s] << setw(52) << oskillnames[n]
                       << ":t" << oskillstats[s] << endl);
                       continue;
                      }
                      else
                      {
                       game.osstostring2(ostringstream().flush() << pskillnames[n] << ":t" << pskillstats[s] << setw(52) << oskillnames[n]
                       << ":t" << oskillstats[s] << endl);
                       continue;
                      }
              }
                  else
                  {
                  game.osstostring2(ostringstream().flush() << "Ваши характеристики:                                Характеристики противника: "
                              << endl);
                  for (int n = 0, s = 0, i = 6;s < i;n++, s++)
                  {
                      if (oskillstats[n] == 10 && n != 0)
                      {
                       game.osstostring2(ostringstream().flush() << oskillnames[n] << ":t" << oskillstats[n] << setw(51) << pskillnames[n]
                       << ":t" << pskillstats[n] << endl);
                       continue;
                      }
                      else if (oskillstats[n] == o.hitpoints)
                      {
                       game.osstostring2(ostringstream().flush() << oskillnames[n] << ":t" << oskillstats[n] << setw(50) << pskillnames[n]
                       << ":t" << pskillstats[n] << endl);
                       continue;
                      }
                      else if (oskillstats[n] == 10 && n == 0)
                      {
                       game.osstostring2(ostringstream().flush() << oskillnames[n] << ":tt" << oskillstats[n] << setw(51) << pskillnames[n]
                       << ":t" << pskillstats[n] << endl);
                       continue;
                      }
                      else if (oskillnames[n].size() < 6)
                      {
                       game.osstostring2(ostringstream().flush() << oskillnames[n] << ":tt" << oskillstats[s] << setw(52) << pskillnames[n]
                       << ":t" << pskillstats[s] << endl);
                       continue;
                      }
                      else
                      {
                       game.osstostring2(ostringstream().flush() << oskillnames[n] << ":t" << oskillstats[s] << setw(52) << pskillnames[n]
                       << ":t" << pskillstats[s] << endl);
                       continue;
                      }
                  }
                  }
              }
               
              void Game::bardisplay(Character &p, Game &game)
              {
                  vector <string> pskillnames = {"Сила","Ловкость","Точность","Выносливость","Скорость","Здоровье","Уровень","Опыт"};
                  vector <double> pskillstats = {p.strength,p.agility,p.accuraty,p.endurance,p.speed,p.hitpoints,p.level,p.experience};
               
                  game.osstostring2(ostringstream().flush() << "Ваши характеристики:" << endl);
                  for (int n = 0, s = 0, i = 8;s < i;n++, s++)
                  {
                      if (pskillstats[n] == 10 && n != 0)
                      {
                       game.osstostring2(ostringstream().flush() << pskillnames[n] << ":t" << pskillstats[n] << endl);
                       continue;
                      }
                      else if (pskillstats[n] == 10 && n == 0)
                      {
                       game.osstostring2(ostringstream().flush() << pskillnames[n] << ":tt" << pskillstats[n] << endl);
                       continue;
                      }
                      else if (pskillnames[n].size() < 6)
                      {
                       game.osstostring2(ostringstream().flush() << pskillnames[n] << ":tt" << pskillstats[s] << endl);
                       continue;
                      }
                      else
                      {
                       game.osstostring2(ostringstream().flush() << pskillnames[n] << ":t"<< pskillstats[s] << endl);
                       continue;
                      }
                  }
              }
               
              int main()
              {
                 setlocale(LC_ALL,"Rus");
                 srand(time(0));
                 Game game;
                 game.play(game);
              }


              Description


              Maxim Ivanov



              2011-12-10 05:51:57 UTC

              Consider the following source code:
              
              struct A
              {
                  static void f() {}
              
                  void foo()
                  {
                      [] () { f(); };
                  }
              };
              
              
              GCC 4.6.1 produces the following error message when compiling it:
              test.cpp: In lambda function:
              test.cpp:7:27: error: ‘this’ was not captured for this lambda function
              
              However, the member function f is static and it's call doesn't use 'this'; therefore the lambda need not to capture 'this'. The code shall compile.


              Comment 1


              Paolo Carlini



              2011-12-22 01:38:46 UTC

              On it.


              Comment 2


              Andy Lutomirski



              2012-05-03 21:53:18 UTC

              This seems to have gotten worse in gcc 4.7.  This code is now rejected as well:
              
              This code:
              
              struct A
              {
                static void func1() {}
              };
              
              template<typename T>
              struct B : public A
              {
                void func2() const
                {
                  func3([&]{ func1(); });
                }
                
                template<typename Func>
                void func3(Func f) const
                {
                }
              };
              
              template class B<int>;
              
              The error is:
              
              template_bug.cc: In instantiation of ‘B<T>::func2() const [with T = int]::<lambda()>’:
              template_bug.cc:11:22:   required from ‘struct B<T>::func2() const [with T = int]::<lambda()>’
              template_bug.cc:11:5:   required from ‘void B<T>::func2() const [with T = int]’
              template_bug.cc:20:16:   required from here
              template_bug.cc:11:16: error: redeclaration of ‘const B<int>* const B<T>::func2() const [with T = int]::<lambda()>::__this’
              template_bug.cc:11:22: note: previous declaration ‘const B<int>* const B<T>::func2() const [with T = int]::<lambda()>::__this’
              template_bug.cc:11:16: error: redeclaration of ‘const B<int>* const this’
              template_bug.cc:11:22: error: ‘const B<int>* const this’ previously declared here
              template_bug.cc:15:8: error: ‘void B<T>::func3(Func) const [with Func = B<T>::func2() const [with T = int]::<lambda()>; T = int]’, declared using local type ‘B<T>::func2() const [with T = int]::<lambda()>’, is used but never defined [-fpermissive]
              
              Your patch fixes this test case, too.


              Comment 4


              gcc-bugx



              2012-06-04 08:21:54 UTC

              Probably related error: this capture ignored on explicit instantiation.
              
              --------------------8<---------------
              struct A
              {
                  static void f() {}
              
                  template <typename T>
                  void foo()
                  {
                      [this] () { f(); };
                  }
              };
              
              template void A::foo<int>();
              -------------------->8---------------
              
              
              Compiler version & output:
              
              $ g++ -std=c++11 -c -v y.cc
              Using built-in specs.
              COLLECT_GCC=g++
              Target: x86_64-unknown-linux-gnu
              Configured with: ./configure --enable-languages=c,c++ --prefix=/home/x
              Thread model: posix
              gcc version 4.7.0 (GCC) 
              COLLECT_GCC_OPTIONS='-std=c++11' '-c' '-v' '-shared-libgcc' '-mtune=generic' '-march=x86-64'
               /home/x/libexec/gcc/x86_64-unknown-linux-gnu/4.7.0/cc1plus -quiet -v -D_GNU_SOURCE y.cc -quiet -dumpbase y.cc -mtune=generic -march=x86-64 -auxbase y -std=c++11 -version -o /tmp/ccdFvfri.s
              GNU C++ (GCC) version 4.7.0 (x86_64-unknown-linux-gnu)
                      compiled by GNU C version 4.7.0, GMP version 4.3.2, MPFR version 3.0.0-p8, MPC version 0.9
              GGC heuristics: --param ggc-min-expand=100 --param ggc-min-heapsize=131072
              ignoring nonexistent directory "/home/x/lib/gcc/x86_64-unknown-linux-gnu/4.7.0/../../../../x86_64-unknown-linux-gnu/include"
              #include "..." search starts here:
              #include <...> search starts here:
               /home/x/lib/gcc/x86_64-unknown-linux-gnu/4.7.0/../../../../include/c++/4.7.0
               /home/x/lib/gcc/x86_64-unknown-linux-gnu/4.7.0/../../../../include/c++/4.7.0/x86_64-unknown-linux-gnu
               /home/x/lib/gcc/x86_64-unknown-linux-gnu/4.7.0/../../../../include/c++/4.7.0/backward
               /home/x/lib/gcc/x86_64-unknown-linux-gnu/4.7.0/include
               /usr/local/include
               /home/x/include
               /home/x/lib/gcc/x86_64-unknown-linux-gnu/4.7.0/include-fixed
               /usr/include
              End of search list.
              GNU C++ (GCC) version 4.7.0 (x86_64-unknown-linux-gnu)
                      compiled by GNU C version 4.7.0, GMP version 4.3.2, MPFR version 3.0.0-p8, MPC version 0.9
              GGC heuristics: --param ggc-min-expand=100 --param ggc-min-heapsize=131072
              Compiler executable checksum: ...
              y.cc: In instantiation of ‘A::foo() [with T = int]::<lambda()>’:
              y.cc:8:4:   required from ‘struct A::foo() [with T = int]::<lambda()>’
              y.cc:8:3:   required from ‘void A::foo() [with T = int]’
              y.cc:11:27:   required from here
              y.cc:8:17: error: ‘this’ was not captured for this lambda function


              Comment 5


              Jason Merrill



              2012-06-04 19:35:40 UTC

              The testcases in comments 2 and 4 are PR 53137, which is fixed for 4.7.1.


              Comment 6


              Paolo Carlini



              2012-08-16 09:53:36 UTC

              Not actively working on this.


              Comment 7


              kpx1894



              2012-12-07 15:18:03 UTC

              This bug is still present in GCC 4.7.2. There are cases where capturing "this" (as a workaround) is not possible:
              ----------
              #include <iostream>
              
              struct Test
              {
                  void (*get())()
                  {
                      return [](){ Test::sf(); };
                  }
              
                  static void sf()
                  {
                      std::cout << "Test::sf" << std::endl;
                  }
              
              };
              
              int main()
              {
                  Test test;
              
                  auto f = test.get();
                  (*f)();
              }
              ----------


              Comment 8


              Jason Merrill



              2013-03-04 18:15:08 UTC

              *** Bug 55828 has been marked as a duplicate of this bug. ***


              Comment 9


              Jason Merrill



              2013-03-08 16:03:57 UTC

              Author: jason
              Date: Fri Mar  8 16:03:48 2013
              New Revision: 196549
              
              URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=196549
              Log:
              	PR c++/51494
              	PR c++/51884
              	PR c++/56222
              	* tree.c (maybe_dummy_object): Don't capture 'this'.
              	* semantics.c (maybe_resolve_dummy): New.
              	(finish_non_static_data_member): Use it.
              	(finish_qualified_id_expr): Don't test is_dummy_object.
              	* cp-tree.h: Declare maybe_resolve_dummy.
              	* call.c (build_new_method_call_1): Use it.
              
              Added:
                  trunk/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-this11.C
              Modified:
                  trunk/gcc/cp/ChangeLog
                  trunk/gcc/cp/call.c
                  trunk/gcc/cp/cp-tree.h
                  trunk/gcc/cp/semantics.c
                  trunk/gcc/cp/tree.c


              Comment 10


              Jason Merrill



              2013-03-08 16:10:48 UTC

              Fixed for 4.8.


              Comment 11


              Arthur O’Dwyer



              2015-11-24 01:18:22 UTC

              Is there a workaround available for GCC 4.6.3?
              That is, I have some code that looks like
              
              class A {
                  static A *unwrap(void *p);
                  static void api_helper(void *p) { A *a = unwrap(p); ... }
                  void init() { register_with_api(&api_helper); }
              };
              
              where "api_helper" exists only to conform to the requirements of the external API.
              To reduce the surface area of the class, I'd like to refactor this into something like
              
              class A {
                  static A *unwrap(void *p);
                  void init() {
                      auto api_helper = [](void *a) { A *a = unwrap(p); ... };
                      register_with_api(api_helper);
                  }
              };
              
              but at the moment I'm hitting this bug in gcc (Ubuntu/Linaro 4.6.3-1ubuntu5) 4.6.3 because "api_helper" happens to also want to use some static members of A.
              
              I understand if there's no workaround (beyond "upgrade to gcc 4.8"), but if there IS one, I'd like to know it!

              У меня есть небольшая проблема, и я не могу понять, почему этот код не работает:

              std::for_each(users.begin(), users.end(), [](Wt::WString u)
              {
              std::cout << "ilosc: " << users.size() << std::endl;
              userBox_->addItem(u);
              });
              

              Ошибки, которые я получаю при компиляции:

              GameWidget.cpp: In lambda function:
              GameWidget.cpp:352:30: error: 'users' is not captured
              GameWidget.cpp:353:4: error: 'this' was not captured for this lambda function
              GameWidget.cpp: In member function 'virtual void GameWidget::updateUsers()':
              GameWidget.cpp:354:3: warning: lambda expressions only available with -std=c++11 or -std=gnu++11 [enabled by default]
              GameWidget.cpp:354:4: error: no matching function for call to 'for_each(std::set<Wt::WString>::iterator, std::set<Wt::WString>::iterator, GameWidget::updateUsers()::<lambda(Wt::WString)>)'
              GameWidget.cpp:354:4: note: candidate is:
              In file included from /usr/include/c++/4.7/algorithm:63:0,
              from GameWidget.h:11,
              from GameWidget.cpp:9:
              /usr/include/c++/4.7/bits/stl_algo.h:4436:5: note: template<class _IIter, class _Funct> _Funct std::for_each(_IIter, _IIter, _Funct)
              GameWidget.cpp:354:4: error: template argument for 'template<class _IIter, class _Funct> _Funct std::for_each(_IIter, _IIter, _Funct)' uses local type 'GameWidget::updateUsers()::<lambda(Wt::WString)>'
              GameWidget.cpp:354:4: error:   trying to instantiate 'template<class _IIter, class _Funct> _Funct std::for_each(_IIter, _IIter, _Funct)'
              

              я использую gcc 4.7.3так что, вероятно, поддержка C ++ 11 доступна для моего компилятора.

              userBox_ это коллекция и BOOST_FOREACH правильно работает для этого кода:

              BOOST_FOREACH(Wt::WString i, users)
              {
              std::cout << "ilosc: " << users.size() << std::endl;
              userBox_->addItem(i);
              }
              

              Спасибо за любой ответ, мне так любопытно, почему это так.

              4

              Решение

              Лямбда, которую вы написали, не фиксирует никаких переменных контекста. Для этого проще всего добавить & в список захвата лямбды. Это захватит все переменные контекста по ссылке, и вы сможете получить к ним доступ в лямбда-выражении.

              std::for_each(users.begin(), users.end(), [&](Wt::WString u)
              {
              std::cout << "ilosc: " << users.size() << std::endl;
              userBox_->addItem(u);
              });
              

              Я не понимаю, почему ты печатаешь users.size() внутри цикла, потому что похоже, что результат будет одинаковым на каждой итерации. Если вы переместите это за пределы цикла и хотите получить более точный контроль над тем, что захватывает лямбда, вы можете изменить список захвата, чтобы захватывать только this указатель. Это позволит вам получить доступ к переменной-члену userBox_,

              std::cout << "ilosc: " << users.size() << std::endl;
              std::for_each(users.begin(), users.end(), [this](Wt::WString u)
              {
              userBox_->addItem(u);
              });
              

              MSDN имеет отличную статью, объясняющую Синтаксис лямбда-выражения в мельчайших подробностях.

              Наконец, в вашем случае нет необходимости std::for_each и лямбда. Было бы гораздо лаконичнее использовать диапазон на основе for цикл для добавления элементов в коллекцию.

              for( auto const& u: users ) {
              userBox_->addItem(u);
              }
              

              8

              Другие решения

              Все, что вам нужно было знать, — это ошибки, которые вы получили.

              Вы явно указали лямбда-выражению не перехватывать что-либо, используя «[]», что означает, что единственными переменными, к которым у него есть доступ внутри тела функции, являются параметры и глобальные переменные.

              Неважно, какой тип userBox_, это переменная-член, поэтому лямбда должна захватывать «this».

              Наконец, вы передаете по значению, что означает, что вы собираетесь дублировать каждый Wt :: WString. Вы можете вместо этого использовать

              std::for_each(users.begin(), users.end(), [&](const Wt::WString& u) {
              ...
              });
              

              «&»захватывает по ссылке и захватит» это «для вас.

              http://en.cppreference.com/w/cpp/language/lambda

              1

              Захват переменных пользователей означает объявление вашей лямбды как:

                  [users](Wt::WString u){...}
              

              который пройдет users как переменная только для чтения.

              Чтобы быть в состоянии изменить users, вам нужно объявить вашу лямбду как:

                  [&users](Wt::WString u){...}
              

              0

              Понравилась статья? Поделить с друзьями:
            • Error this username is already registered please choose another one
            • Error this statement may fall through werror implicit fallthrough
            • Error this server is already on your list ok
            • Error this script needs bsddb3 to be installed
            • Error this script must be started from web server s document root