Twitter iPhone pliant OnePlus 11 PS5 Disney+ Orange Livebox Windows 11

Mutable & références

5 réponses
Avatar
Yann Renard
Bonjour à tous,

dans la dernière version de GCC, il y a un correctif qui empêche de
déclarer les références mutable.

<http://gcc.gnu.org/bugzilla/show_bug.cgi?id=33558>

Qu'est ce qui motive une telle restriction dans la norme alors que cela
reste possible avec des pointeurs ?

Merci d'avance et bonne journée,
Yann

5 réponses

Avatar
Pascal J. Bourguignon
Yann Renard writes:

Bonjour à tous,

dans la dernière version de GCC, il y a un correctif qui empêche de
déclarer les références mutable.

<http://gcc.gnu.org/bugzilla/show_bug.cgi?id3558>

Qu'est ce qui motive une telle restriction dans la norme alors que
cela reste possible avec des pointeurs ?



Les références ne sont pas mutables, et ne l'ont jamais été.


int f(){
int bB;
int c$;
int& a=b;

/* Il n'y a pas moyen de changer a pour lui faire référencer c au lieu
de b. */

a=c; /* assigne 24 à b */
a=&c; /* signale une erreur pour assignement d'un pointeur à un b qui est int */

return(a);
}



--
__Pascal Bourguignon__ http://www.informatimago.com/
A bad day in () is better than a good day in {}.
Avatar
Yann Renard
On 08/04/2011 11:39 AM, Pascal J. Bourguignon wrote:
Yann Renard writes:

Bonjour à tous,

dans la dernière version de GCC, il y a un correctif qui empêche de
déclarer les références mutable.

<http://gcc.gnu.org/bugzilla/show_bug.cgi?id3558>

Qu'est ce qui motive une telle restriction dans la norme alors que
cela reste possible avec des pointeurs ?



Les références ne sont pas mutables, et ne l'ont jamais été.


int f(){
int bB;
int c$;
int& a=b;

/* Il n'y a pas moyen de changer a pour lui faire référencer c au lieu
de b. */

a=c; /* assigne 24 à b */
a=&c; /* signale une erreur pour assignement d'un pointeur à un b qui est int */

return(a);
}



Merci Pascal pour cette réponse mais je crois qu'elle ne répond pas à ma
question.

Voici un peu de code pour illustrer mon propos :

class A
{
public:
A(B& ref) _b(b) { }

// Je veux exposer une ref non const de B
// tout en préservant A
B& get() const { return _b; }

private:
mutable B& _b;
};

le "mutable B& _b;" n'est pas autorisé (mais compilait quand même avec
les versions précédents de GCC et les versions actuelles de Visual
Studio d'ailleurs).

Yann
Avatar
Pascal J. Bourguignon
Yann Renard writes:

On 08/04/2011 11:39 AM, Pascal J. Bourguignon wrote:
Yann Renard writes:

Bonjour à tous,

dans la dernière version de GCC, il y a un correctif qui empêche de
déclarer les références mutable.

<http://gcc.gnu.org/bugzilla/show_bug.cgi?id3558>

Qu'est ce qui motive une telle restriction dans la norme alors que
cela reste possible avec des pointeurs ?



Les références ne sont pas mutables, et ne l'ont jamais été.


int f(){
int bB;
int c$;
int& a=b;

/* Il n'y a pas moyen de changer a pour lui faire référencer c au lieu
de b. */

a=c; /* assigne 24 à b */
a=&c; /* signale une erreur pour assignement d'un pointeur à un b qui est int */

return(a);
}



Merci Pascal pour cette réponse mais je crois qu'elle ne répond pas à
ma question.

Voici un peu de code pour illustrer mon propos :





class A
{
public:
A(B& ref) _b(b) { }

// Je veux exposer une ref non const de B
// tout en préservant A
B& get() const { return _b; }

private:
B a;
B c;
mutable B& _b;

void f(){
/* Il n'y a pas moyen de changer a pour lui faire référencer a ou c
au lieu de ce avec quoi il a été initialisé. */
b=a; /* assigne a à b */
b=&c; /* signale une erreur pour assignement d'un pointeur à un B */
}
};

le "mutable B& _b;" n'est pas autorisé (mais compilait quand même avec
les versions précédents de GCC et les versions actuelles de Visual
Studio d'ailleurs).




--
__Pascal Bourguignon__ http://www.informatimago.com/
A bad day in () is better than a good day in {}.
Avatar
Alain Ketterlin
Yann Renard writes:

Voici un peu de code pour illustrer mon propos :

class A
{
public:
A(B& ref) _b(b) { }

// Je veux exposer une ref non const de B
// tout en préservant A
B& get() const { return _b; }

private:
mutable B& _b;
};



Tu te trompes : mutable ici s'applique à la référence, pas à l'objet
(l'objet est déjà modifiable, sans autre forme de procès). E n substance,
tu dis que le membre _b d'un A const peut être modifié. Or ce n'e st pas
vrai, puisque c'est une référence et qu'une référence n e peut jamais
être modifiée.

mutable qualifie un membre, pas un type.

le "mutable B& _b;" n'est pas autorisé (mais compilait quand mê me avec
les versions précédents de GCC et les versions actuelles de Vis ual
Studio d'ailleurs).



C'est un oubli manifeste, puisque qu'une "référence mutable" (ou une
"référence non const") est un oxymore, ça n'existe pas, par définition
des références.

-- Alain.
Avatar
Alain Ketterlin
Yann Renard writes:

[...]
class A
{
public:
A() _a(a) { }



Il manque un :


int& get() const
{
// la référence ne change pas
// mais l'un des membres de A
// change quand même
_a = 1;
return _a;
}

private:
int a;
int& _a;
};

C'est assez troublant.



const est un qualificateur de type, pas de "donnée" ou "d'objet". Au
moment où tu fais "_a = 1", le type de _a est int&, à savoir ri en qui
empêche d'écrire dans l'int référencé.

Le compilateur ne peut pas savoir que la référence désigne e n fait un
membre de l'objet (const) en cours de manipulation. (Même si il le
pouvait dans ce cas, dans le cas général c'est impossible.) C'est
exactement la même chose avec les pointeurs. Tu peux écrire :

class A
{
public:
A() : _a(&a) { }
int * get() const
{
*_a = 1;
return _a;
}
private:
int a;
int * _a;
};

-- Alain.