O valor deste ponteiro é constante durante a vida útil do objeto?

19

É thisgarantido que o valor do ponteiro seja constante durante a vida útil de um objeto específico? Não consigo imaginar um caso em que isso mudaria, mas não sei se não estou perdendo alguma coisa.

Daniel Langr
fonte
4
O valor do thisponteiro sempre é o valor do endereço do objeto no qual a função foi chamada. Portanto, a pergunta é equivalente a 'um objeto pode mudar seu endereço de memória ao longo da vida?'
Aconcagua
2
Vale a pena notar: se alguém fala informalmente sobre a vida útil, um objeto que é movido via std::movemudaria de thisponteiro. Formalmente, diríamos que esses são dois objetos diferentes, mas, informalmente, podemos pensar neles como "o mesmo", o que pode gerar confusão se não estiver prestando atenção.
Cort Ammon

Respostas:

27

É thisgarantido que o valor do ponteiro seja constante durante a vida útil de um objeto específico?

Sim .

Como o usuário Aconcagua coloca: o valor do thisponteiro sempre é o valor do endereço do objeto no qual a função foi chamada 1 . Portanto, a pergunta é equivalente a:

Um objeto pode alterar seu endereço de memória ao longo da vida útil?

Isso não é possível, por definição de lifetime2 . A vida útil de um objeto começa quando ou após seu armazenamento ser obtido e termina antes de quando ele é liberado.


1) [class.this]/1

No corpo de um não-estático ( [class.mfct]função de membro), a palavra-chave thisé uma prvalue cujo valor é um apontador para o objecto para o qual a função é chamada.

2) [basic.life]/1 (ênfase minha)

A vida útil de um objeto ou referência é uma propriedade de tempo de execução do objeto ou referência. Diz-se que uma variável possui inicialização vazia se for inicializada por padrão e, se for do tipo de classe ou de uma matriz (possivelmente multidimensional), esse tipo de classe possui um construtor padrão trivial. A vida útil de um objeto do tipo Tcomeça quando :

  • é obtido um armazenamento com o alinhamento e tamanho adequados para o tipoT e
  • sua inicialização (se houver) estiver concluída (incluindo inicialização vazia) ( [dcl.init]), exceto que se o objeto for um membro da união ou um subobjeto do mesmo, sua vida útil somente começará se esse membro da união for o membro inicializado na união ( [dcl.init.aggr], [class.base.init]) ou como descrito em [class.union].

A vida útil de um objeto odo tipo Ttermina quando :

  • se Tfor um tipo que não seja de classe, o objeto será destruído ou
  • se Tfor um tipo de classe, a chamada destruidora será iniciada ou
  • o armazenamento que o objeto ocupa é liberado ou é reutilizado por um objeto que não está aninhado em o( [intro.object]).
YSC
fonte
Isso significa que seria impossível (ilegal) para um tempo de execução suficientemente complexo implementar a compactação automatizada de memória para um programa C ++? Ou significa apenas que precisaria se comportar "como se", de modo a fornecer o mesmo valor de thistodas as vezes, independentemente dos movimentos na pilha?
Alexander - Restabelecer Monica
2
@ Alex claramente a regra de como prevalece. Sempre.
YSC 15/01
11
@ Alexander-ReinstateMonica a vtable é um conceito semelhante que reduz o desempenho, mas é aceito, pois os benefícios superam a desvantagem. Processadores modernos são realmente eficientes com indireção.
Mark Ransom
11
@MarkRansom " é um ponteiro garantido para ser o endereço de um objeto ou o compilador está livre para adicionar um nível de indireção? " Por definição, que ptr é o endereço de um objeto, mas "endereço" pode ser um conceito abstrato de alto nível . Mas se você introduzir indiretamente, precisará de atomicidade, precisará de bloqueio, precisará de um monte de trabalho adicional em todos os acessos de qualquer objeto, se houver threads. Simplesmente pela aparência, posso fazê-lo é impraticável (e nem sequer considerei o fato de que o C / C ++ também funciona como uma linguagem de baixo nível).
curiousguy
11
@curiousguy você faz bons pontos, e não estou mais argumentando que a indireção seria prática. Ainda faz um bom experimento mental.
Mark Ransom
8

Um objeto tem uma região de armazenamento. thisaponta lá.

[intro.object]/1

Um objeto ocupa uma região de armazenamento em seu período de construção ( [class.cdtor]), durante toda a sua vida útil e em seu período de destruição ( [class.cdtor]).

Caleth
fonte
-1

thisÉ garantido que o valor de seja constante se o programa o ler, se subsequentemente alguns bits do valor de leitura forem impossíveis de coletar no lixo ou se subsequentemente alguns bits do valor de leitura tiverem escapado para fora do programa. Em todos os outros casos, ele se comporta como o gato de Schrödinger, ou seja, é constante e variável ao mesmo tempo.

símbolo do átomo
fonte
Desculpe, não entendo nada. O que é coletar lixo e escapar fora do programa ?
Daniel Langr 23/01
@DanielLangr Os bits do valor do identificadorthis
atomsymbol
Isso não responde à minha pergunta. O que é o lixo coletar alguns bits? Ou para escapar deles fora do programa?
Daniel Langr 23/01
@DanielLangr É difícil explicar em um pequeno pedaço de texto
atomsymbol