OVH Cloud OVH Cloud

A quoi servent > pour les entiers?

31 réponses
Avatar
Michaël Delva
Bonjour,

j'ai souvent vu ces opérateurs utilisés pour des entiers, avec le terme
décalage associé, mais je ne sais pas à quoi cela sert réellement...

Une âme charitable pourrait m'éclairer?

Merci d'avance

10 réponses

1 2 3 4
Avatar
kanze
Jean-Marc Bourguet wrote in message
news:...
writes:

Cette dernière paragraphe me semble exactement la définition des
opérateurs &, | et ^ en C++. Y compris la mauvaise précédence:-).


Euh, la precedence des operateurs en Ada ne depend pas des types
utilises.


Et on veut avoir la précédence voulue pour les booléens. Ça, j'avais
bien compris. N'empêche que pour les modular, c'est exactement comme en
C/C++, y compris que la précédence ne convient pas vraiment. (Je suis
d'accord que le fait qu'en Ada, c'est le même opérateur, et qu'on ne
veut pas que la précédence dépend des types, est une justification de
poids. Qui manque en C/C++.)

Et le and booleen ou le and binaire, c'est le meme operateur. Par
contre si j'ai bonne memoire, and et or ont la meme precedence et pas
de priorite (autrement dit les parentheses sont obligatoires quand on
les melange). Mais je parlais des decalages, pas des autres
operations.

Il y a aussi un « not » dans §4.5.6, avec des sémantiques (pour un
type « modular ») qui correspond à ! en C++.


Non, le not correspond a ~ (a moins qu'il y en ai aussi un qui
correspond a ! ce qui est possible avec la surcharge sur le type
resultat des fonctions/operateurs mais j'en doute, ce n'est pas
tellement dans la philosophie Ada).


Non, c'est moi qui s'est trompé de touche. Il correspond bien à ~.

Sauf dans le cas où il s'applique à un boolean. Dans ce cas-là, en C++,
~true est toujours true, tandis qu'en Ada, « not true » est false.

Les types modular ont globalement la meme semantique que les unsigned
en C++ (a part qu'on peut s'amuser a avoir des modular sur autre chose
que les puissances de 2, mais la le comite s'est amuse). Il y a
Natural pour la semantique que certains aimeraient donner a unsigned
:-)


Je crois qu'on peut dire que pour les « petits » types, le système de
types d'Ada est beaucoup plus puissant et plus souple que celui de C++.
Quand on commence à définir des classes, avec comportement, en revanche,
je ne sais pas. Je n'ai pas d'expérience avec Ada pour dire, mais j'ai
du mal à imaginer quelque chose de plus souple que ce qu'offre le C++.

En revanche, je ne trouve pas de décalages, même dans les fonctions
prédéfinies (Appendice A). Mais peut-être je ne sais pas où
chercher.


C'est donc mon souvenir (si j'ai bonne memoire, gnat a des fonctions
intrinseques pour ca et peut-etre meme les rotations, mais ce n'est
pas standard).


Ce qui m'a un peu étonné. Tous les Pascal et les Modula dont je me suis
servis en avait. L'utilité en était donc bien connue.

Naturellement, un moyen naturel en Ada (le seul disponible en Ada83;
en Ada95 il y a en plus les modular) de manipuler des bits, c'est
d'utiliser des tableaux (compactes) de booleens.


D'une part, il ne s'agit pas seulement de manipuler les bits. La seule
utilisation que j'en fais, c'est d'insérer et d'extraire des champs dans
les octets, ou éventuellement des mots, surtout pour être conforme à un
format binaire externe -- protocol de transmission, etc. C-à-d que dans
un octet, je peux être amener à traiter deux champs de 3 bits, et deux
d'un bit. Ou un champs de 4 bits et deux de 2. C'est donc un espèce de
struct avec bit fields dont j'ai besoin.

De l'autre part, la disposition physique m'importe énormement.
Conceptuellement, j'ai exactement ce qu'il me faut avec les bit fields
de C/C++. Dans la pratique, en revanche, le fait que la norme n'impose
aucune disposition physique en mémoire, et que les compilateurs varient
réelement de l'un à l'autre à cet égard, les rend inutilisable pour
cette application.

Auquel cas la concatenation de tableaux et l'utilisation d'intervalles
permettent d'exprimer les operations naturellements (et c'est
vraissemblablement des idiomes reconnus pas les compilateurs -- j'ai
jamais verifie en Ada mais les synthetiseurs VHDL le font).


C-à-d que la spécification d'Ada exige une certaine disposition dans la
mémoire ? Que si j'écris quelque chose comme :

record Header
flag1 : Boolean ;
id1 : mod 8 ;
flag2 : Boolean ;
id2 : mod 8 ;
end record ;

je suis garantie d'avoir une structure d'un octet, avec flag1 sur le bit
7, id1 sur les bits 6-4, flag2 sur le bit 3 et id2 sur les bits 2-0 ?

À titre d'exemple, si j'écris en C++ :

struct Header
{
bool flag1 : 1 ;
unsigned id1 : 3 ;
bool flag2 : 1 ;
unsigned id2 : 3 ;
} ;

j'ai déjà sizeof( Header ) == 4 avec les compilateurs auxquels j'ai
accès sous Solaris (or que le but, c'est de décrire le format d'un octet
-- format imposé par un protocol de transmission). Et l'ordre des champs
dans le mot (ou l'octet du mot) n'est pas spécifié non plus.

Par exemple
A = A(A'Low) & A(A'Hight .. A'Low+1);
pour une rotation.

(Euh, si on continue comme ca, il va falloir mettre fcla en copie, ne
fut-ce que pour corriger ma memoire.)


Tout à fait. Parce que pour commencer, je ne comprends pas du tout ton
Ada. (Probablement parce que je ne connais pas Ada, pour commencer:-).)

--
James Kanze GABI Software http://www.gabi-soft.fr
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34


Avatar
Jean-Marc Bourguet
writes:

Jean-Marc Bourguet wrote in message
news:...
writes:

Les types modular ont globalement la meme semantique que les
unsigned en C++ (a part qu'on peut s'amuser a avoir des modular
sur autre chose que les puissances de 2, mais la le comite s'est
amuse). Il y a Natural pour la semantique que certains aimeraient
donner a unsigned :-)


Je crois qu'on peut dire que pour les « petits » types, le système
de types d'Ada est beaucoup plus puissant et plus souple que celui
de C++. Quand on commence à définir des classes, avec comportement,
en revanche, je ne sais pas. Je n'ai pas d'expérience avec Ada pour
dire, mais j'ai du mal à imaginer quelque chose de plus souple que
ce qu'offre le C++.


A ma connaissance, les seuls points ou C++ a une souplesse
incontestable en plus qu'Ada, c'est la gestion de la genericite et
l'heritage multiple. Et je ne suis pas sur que les complications de
l'heritage multiple complet comme en C++ vaillent la peine (un
heritage multiple restreint comme en Java -- disons un ou on ne peux
pas ajouter des membres donnees -- me semble un bon compromis, et
c'etait la voie prise par le comite de normalisation Ada la derniere
fois que j'ai regarde).

Pour le reste c'est ou bien mitige (les deux ont les defaults de leurs
qualites) ou bien a l'avantage d'Ada (taches/threads et programme
distribue totalement hors langage en C++ par exemple).

En revanche, je ne trouve pas de décalages, même dans les
fonctions prédéfinies (Appendice A). Mais peut-être je ne sais
pas où chercher.


C'est donc mon souvenir (si j'ai bonne memoire, gnat a des
fonctions intrinseques pour ca et peut-etre meme les rotations,
mais ce n'est pas standard).


Ce qui m'a un peu étonné. Tous les Pascal et les Modula dont je me
suis servis en avait. L'utilité en était donc bien connue.

Naturellement, un moyen naturel en Ada (le seul disponible en
Ada83; en Ada95 il y a en plus les modular) de manipuler des bits,
c'est d'utiliser des tableaux (compactes) de booleens.


D'une part, il ne s'agit pas seulement de manipuler les bits. La
seule utilisation que j'en fais, c'est d'insérer et d'extraire des
champs dans les octets, ou éventuellement des mots, surtout pour
être conforme à un format binaire externe -- protocol de
transmission, etc. C-à-d que dans un octet, je peux être amener à
traiter deux champs de 3 bits, et deux d'un bit. Ou un champs de 4
bits et deux de 2. C'est donc un espèce de struct avec bit fields
dont j'ai besoin.

De l'autre part, la disposition physique m'importe énormement.
Conceptuellement, j'ai exactement ce qu'il me faut avec les bit
fields de C/C++. Dans la pratique, en revanche, le fait que la norme
n'impose aucune disposition physique en mémoire, et que les
compilateurs varient réelement de l'un à l'autre à cet égard, les
rend inutilisable pour cette application.

Auquel cas la concatenation de tableaux et l'utilisation
d'intervalles permettent d'exprimer les operations naturellements
(et c'est vraissemblablement des idiomes reconnus pas les
compilateurs -- j'ai jamais verifie en Ada mais les synthetiseurs
VHDL le font).


C-à-d que la spécification d'Ada exige une certaine disposition dans
la mémoire ? Que si j'écris quelque chose comme :

record Header
flag1 : Boolean ;
id1 : mod 8 ;
flag2 : Boolean ;
id2 : mod 8 ;
end record ;

je suis garantie d'avoir une structure d'un octet, avec flag1 sur le
bit 7, id1 sur les bits 6-4, flag2 sur le bit 3 et id2 sur les bits
2-0 ?


Avec ce que tu as ecrit, la seule garantie c'est que le compilateur
refuse. Avec

type Mod8 is mod 8;
type Header is record
flag1 : Boolean;
id1 : Mod8;
flag2 : Boolean;
id2 : Mod8;
end record;

Tu n'as aucune garantie. Si tu mets en plus un
pragma Packet(Header); -- syntaxe a verifier
tu as le mieux que peut faire le compilateur, vraissemblablement ce
que tu veux. Tu peux aussi utiliser
for Header'size use 1; -- a nouveau syntaxe a verifier
qui force l'erreur de compilation si le compilateur n'arrive pas a
mettre tout sur 1 byte.

Tu peux etre plus precis en specifiant exactement ce que tu veux, y
compris la presence de bits de padding (recherche "representation
clause", ce qui est la troisieme maniere de faire des manipulations a
ce niveau que j'avais oublie parce qu'elle est implicite).

A ce niveau, il y a une difference entre
- ce que le langage est capable d'exprimer
- ce que les compilateurs acceptent de faire
- ce que la norme exige comme capacite minimale
Autrement dit ce n'est pas toujours portable.

Par exemple
A = A(A'Low) & A(A'Hight .. A'Low+1);
pour une rotation.

(Euh, si on continue comme ca, il va falloir mettre fcla en copie, ne
fut-ce que pour corriger ma memoire.)


Tout à fait. Parce que pour commencer, je ne comprends pas du tout ton
Ada. (Probablement parce que je ne connais pas Ada, pour commencer:-).)


Si je te dis que le & est l'operateur de concatenation en Ada et que
A'Low designe l'indice le plus petit du tableau et A'High l'indice le
plus grand ca suffit?

Copie sur fr.comp.lang.ada, pas de suivi pour le moment.

A+

--
Jean-Marc
FAQ de fclc++: http://www.cmla.ens-cachan.fr/~dosreis/C++/FAQ
C++ FAQ Lite en VF: http://www.ifrance.com/jlecomte/c++/c++-faq-lite/index.html
Site de usenet-fr: http://www.usenet-fr.news.eu.org



Avatar
Eric Jacoboni
Jean-Marc Bourguet writes:

A ma connaissance, les seuls points ou C++ a une souplesse
incontestable en plus qu'Ada, c'est la gestion de la genericite


Ahem ;-)

Avec ce que tu as ecrit, la seule garantie c'est que le compilateur
refuse. Avec

type Mod8 is mod 8;
type Header is record
flag1 : Boolean;
id1 : Mod8;
flag2 : Boolean;
id2 : Mod8;
end record;


En fait, mod est suivi du modulo, pas du nbre de bits.

Par exemple
A = A(A'Low) & A(A'Hight .. A'Low+1);
pour une rotation.



Si je te dis que le & est l'operateur de concatenation en Ada et que
A'Low designe l'indice le plus petit du tableau et A'High l'indice le
plus grand ca suffit?


1) En Ada, l'affectation est notée ':=', pas '=' ;-)
2) Les attributs que tu appelles Low et High sont, en fait, First et Last

3) En Ada, un intervalle qui aurait sa borne inférieure plus grande
que sa borne supérieure serait considéré comme vide. La tranche
A(A'Last .. A'First + 1) lèverait donc Constraint_Error.


Vite fait, un truc qui compile :

% cat TestA.adb
with Ada.Text_Io; use Ada.Text_Io;

procedure TestA is
type Mod8 is mod 256;
A : array(1..10) of Mod8 := (1, 2, 3, 4, 5, 6, 7, 8, 9, 10);
begin
for I in A'Range loop
Put(Mod8'Image(A(I)) & ", ");
end loop;
New_Line;

-- A := A(A'First) & A(A'Last .. A'First + 1); -- Constraint Error
A := A(A'First + 1 .. A'Last) & A(A'First); -- Rotation à droite
for I in A'Range loop
Put(Mod8'Image(A(I)) & ", ");
end loop;
New_Line;

A := A(A'Last) & A(A'First .. A'Last - 1); -- Rotation à gauche
for I in A'Range loop
Put(Mod8'Image(A(I)) & ", ");
end loop;
New_Line;

end TestA;

% ./testa
1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
2, 3, 4, 5, 6, 7, 8, 9, 10, 1,
1, 2, 3, 4, 5, 6, 7, 8, 9, 10,

[Suivi to fcla]
--
Éric Jacoboni, né il y a 1392134629 secondes



Avatar
Eric Jacoboni
writes:

C-à-d que la spécification d'Ada exige une certaine disposition dans la
mémoire ? Que si j'écris quelque chose comme :

record Header
flag1 : Boolean ;
id1 : mod 8 ;
flag2 : Boolean ;
id2 : mod 8 ;
end record ;

je suis garantie d'avoir une structure d'un octet, avec flag1 sur le bit
7, id1 sur les bits 6-4, flag2 sur le bit 3 et id2 sur les bits 2-0 ?


Je ne sais pas si cela répondra à ta question, mais un exemple de
représentation est donnée dans l'ARM95 (voir en bas de la page
<http://www.grammatech.com/rm95html-1.0/rm9x-13-05-01.html#1>)

Concernant les décalages et autres opérations de bas niveau, l'annexe
B.2 de ARM95 présente le paquetage Interfaces, qui dispose, entre
autres, des opérations suivantes :

type Integer_n is range -2**(n-1) .. 2**(n-1) - 1; --2's complement
type Unsigned_n is mod 2**n;

function Shift_Left (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;
function Shift_Right (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;
function Shift_Right_Arithmetic (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;
function Rotate_Left (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;
function Rotate_Right (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;

Donc, en gros (avec Gnat) :

with Ada.Text_Io; use Ada.Text_Io;
with Interfaces; use Interfaces;

procedure Test_Shift is

package Byte_IO is new Integer_IO(Integer_8);

Un_Octet : Unsigned_8 := 2#0010_1010#;
begin
Byte_IO.Put(Integer_8(Un_Octet), Base => 2);
New_Line;
Un_Octet := Shift_Right(Un_Octet, 1);
Byte_IO.Put(Integer_8(Un_Octet), Base => 2);
New_Line;
end;

% test_shift
2#101010#
2#10101#

[fu2 fcla]
--
Éric Jacoboni, né il y a 1392137999 secondes

Avatar
Eric Jacoboni
writes:

C-à-d que la spécification d'Ada exige une certaine disposition dans la
mémoire ? Que si j'écris quelque chose comme :

record Header
flag1 : Boolean ;
id1 : mod 8 ;
flag2 : Boolean ;
id2 : mod 8 ;
end record ;

je suis garantie d'avoir une structure d'un octet, avec flag1 sur le bit
7, id1 sur les bits 6-4, flag2 sur le bit 3 et id2 sur les bits 2-0 ?


Je ne sais pas si cela répondra à ta question, mais un exemple de
représentation est donnée dans l'ARM95 (voir en bas de la page
<http://www.grammatech.com/rm95html-1.0/rm9x-13-05-01.html#1>)

Concernant les décalages et autres opérations de bas niveau, l'annexe
B.2 de ARM95 présente le paquetage Interfaces, qui dispose, entre
autres, des opérations suivantes :

type Integer_n is range -2**(n-1) .. 2**(n-1) - 1; --2's complement
type Unsigned_n is mod 2**n;

function Shift_Left (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;
function Shift_Right (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;
function Shift_Right_Arithmetic (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;
function Rotate_Left (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;
function Rotate_Right (Value : Unsigned_n; Amount : Natural)
return Unsigned_n;

Donc, en gros (avec Gnat) :

with Ada.Text_Io; use Ada.Text_Io;
with Interfaces; use Interfaces;

procedure Test_Shift is

package Byte_IO is new Integer_IO(Integer_8);

Un_Octet : Unsigned_8 := 2#0010_1010#;
begin
Byte_IO.Put(Integer_8(Un_Octet), Base => 2);
New_Line;
Un_Octet := Shift_Right(Un_Octet, 1);
Byte_IO.Put(Integer_8(Un_Octet), Base => 2);
New_Line;
end;

% test_shift
2#101010#
2#10101#

[fu2 fcla]
--
Éric Jacoboni, né il y a 1392137999 secondes

Avatar
kanze
Jean-Marc Bourguet wrote in message
news:...
writes:

Jean-Marc Bourguet wrote in message
news:...
writes:

Les types modular ont globalement la meme semantique que les
unsigned en C++ (a part qu'on peut s'amuser a avoir des modular
sur autre chose que les puissances de 2, mais la le comite s'est
amuse). Il y a Natural pour la semantique que certains aimeraient
donner a unsigned :-)


Je crois qu'on peut dire que pour les « petits » types, le système
de types d'Ada est beaucoup plus puissant et plus souple que celui
de C++. Quand on commence à définir des classes, avec comportement,
en revanche, je ne sais pas. Je n'ai pas d'expérience avec Ada pour
dire, mais j'ai du mal à imaginer quelque chose de plus souple que
ce qu'offre le C++.


A ma connaissance, les seuls points ou C++ a une souplesse
incontestable en plus qu'Ada, c'est la gestion de la genericite et
l'heritage multiple. Et je ne suis pas sur que les complications de
l'heritage multiple complet comme en C++ vaillent la peine (un
heritage multiple restreint comme en Java -- disons un ou on ne peux
pas ajouter des membres donnees -- me semble un bon compromis, et
c'etait la voie prise par le comite de normalisation Ada la derniere
fois que j'ai regarde).


J'avoue que je ne connais pas du tout l'Ada. Je connais des types de
sous-intervale de Pascal et de Modula, et ils me manquent en C/C++. J'ai
régardé la chapitre de la norme Ada pour les types entiers pour savoir
exactement ce que c'était qu'un type « modular », après avoir lu la
définition des opérateurs and, or et xor ; ce que j'ai lu m'a plû
beaucoup.

En ce qui concerne les classes, je n'ai pas la moindre idée de ce
qu'offre réelement Ada. En revanche, j'ai du mal à imaginer quoique ce
soit qu'on pourrait offrir qui n'est pas en C++.

Et en ce qui concerne l'héritage multiple : je m'en sers assez souvent.
Et si ce n'est pas tous les jours que les classes de base ont des
membres données, ça arrive quand même de temps en temps d'utiliser des
mixins.

Pour le reste c'est ou bien mitige (les deux ont les defaults de leurs
qualites) ou bien a l'avantage d'Ada (taches/threads et programme
distribue totalement hors langage en C++ par exemple).


Les taches et les threads jouent sur le typage ?

[...]
Auquel cas la concatenation de tableaux et l'utilisation
d'intervalles permettent d'exprimer les operations naturellements
(et c'est vraissemblablement des idiomes reconnus pas les
compilateurs -- j'ai jamais verifie en Ada mais les synthetiseurs
VHDL le font).


C-à-d que la spécification d'Ada exige une certaine disposition dans
la mémoire ? Que si j'écris quelque chose comme :

record Header
flag1 : Boolean ;
id1 : mod 8 ;
flag2 : Boolean ;
id2 : mod 8 ;
end record ;

je suis garantie d'avoir une structure d'un octet, avec flag1 sur le
bit 7, id1 sur les bits 6-4, flag2 sur le bit 3 et id2 sur les bits
2-0 ?


Avec ce que tu as ecrit, la seule garantie c'est que le compilateur
refuse. Avec

type Mod8 is mod 8;
type Header is record
flag1 : Boolean;
id1 : Mod8;
flag2 : Boolean;
id2 : Mod8;
end record;

Tu n'as aucune garantie. Si tu mets en plus un
pragma Packet(Header); -- syntaxe a verifier
tu as le mieux que peut faire le compilateur, vraissemblablement ce
que tu veux.


Est-ce que j'ai une garantie en ce qui concerne l'ordre dans le mot.
Avec des bit fields en C++, je ne saurais pas si flag1 se trouve sur le
bit le plus fort, ou le bit le plus faible, par exemple. (Avec les
compilateurs dont je dispose sous Solaris, par exemple, la déclaration
équivalente avec des bit fields donne un objet de quatre octets, avec
flag1 sur le bit 31, etc. Mais je me suis servi des compilateurs qui
mettaient flag1 sur le bit 0.)

Tu peux aussi utiliser
for Header'size use 1; -- a nouveau syntaxe a verifier
qui force l'erreur de compilation si le compilateur n'arrive pas a
mettre tout sur 1 byte.


Il faut non seulement que ça tient sur un octet, il faut que l'ordre des
bits correspond. D'après mes expériences en C/C++, dans un monde
grand-boutien (comme sous Solaris), il est normal que le premier champ
se place sur les bits de poids forts ; dans un monde petit-boutien, en
revanche, c'est le contraire qui est plus fréquent (d'après mes
souvenirs, en tout cas).

Tu peux etre plus precis en specifiant exactement ce que tu veux, y
compris la presence de bits de padding (recherche "representation
clause", ce qui est la troisieme maniere de faire des manipulations a
ce niveau que j'avais oublie parce qu'elle est implicite).

A ce niveau, il y a une difference entre
- ce que le langage est capable d'exprimer
- ce que les compilateurs acceptent de faire
- ce que la norme exige comme capacite minimale
Autrement dit ce n'est pas toujours portable.


Mais si ça compile, j'ai ce que je veux:-).

Par exemple
A = A(A'Low) & A(A'Hight .. A'Low+1);
pour une rotation.

(Euh, si on continue comme ca, il va falloir mettre fcla en copie,
ne fut-ce que pour corriger ma memoire.)


Tout à fait. Parce que pour commencer, je ne comprends pas du tout
ton Ada. (Probablement parce que je ne connais pas Ada, pour
commencer:-).)


Si je te dis que le & est l'operateur de concatenation en Ada et que
A'Low designe l'indice le plus petit du tableau et A'High l'indice le
plus grand ca suffit?


Oui. Pour ce cas-ci, en tout cas. Mon expérience avec les langages de la
famille Pascal ne me permet pas à déviner ce que signifie l'opérateur '.

Mais je vois qu'il va falloir que je me mets à Ada. Ne serait-ce que
pour avoir quelque chose à comparer avec le C++.

--
James Kanze GABI Software http://www.gabi-soft.fr
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34



Avatar
Jean-Marc Bourguet
writes:

Jean-Marc Bourguet wrote in message
news:...

Pour le reste c'est ou bien mitige (les deux ont les defaults de leurs
qualites) ou bien a l'avantage d'Ada (taches/threads et programme
distribue totalement hors langage en C++ par exemple).


Les taches et les threads jouent sur le typage ?


Les taches se comportent comme des types (je ne sais plus si ce sont
des types formellement ou pas, mais c'est une bonne premiere
approximation). Tu peux faire une liste chainee de taches si tu veux.
Et les types proteges, ca n'a de sens qu'avec des taches.

[...]
Tu n'as aucune garantie. Si tu mets en plus un
pragma Packet(Header); -- syntaxe a verifier
tu as le mieux que peut faire le compilateur, vraissemblablement ce
que tu veux.


Est-ce que j'ai une garantie en ce qui concerne l'ordre dans le mot.


Non.
[...]
Tu peux aussi utiliser
for Header'size use 1; -- a nouveau syntaxe a verifier
qui force l'erreur de compilation si le compilateur n'arrive pas a
mettre tout sur 1 byte.


Il faut non seulement que ça tient sur un octet, il faut que l'ordre des
bits correspond.


Pas garanti non plus.

[...]
Tu peux etre plus precis en specifiant exactement ce que tu veux, y
compris la presence de bits de padding (recherche "representation
clause", ce qui est la troisieme maniere de faire des manipulations a
ce niveau que j'avais oublie parce qu'elle est implicite).

A ce niveau, il y a une difference entre
- ce que le langage est capable d'exprimer
- ce que les compilateurs acceptent de faire
- ce que la norme exige comme capacite minimale
Autrement dit ce n'est pas toujours portable.


Mais si ça compile, j'ai ce que je veux:-).


Gagne.

Par exemple
A = A(A'Low) & A(A'Hight .. A'Low+1);
pour une rotation.

(Euh, si on continue comme ca, il va falloir mettre fcla en copie,
ne fut-ce que pour corriger ma memoire.)


Tout à fait. Parce que pour commencer, je ne comprends pas du tout
ton Ada. (Probablement parce que je ne connais pas Ada, pour
commencer:-).)


Si je te dis que le & est l'operateur de concatenation en Ada et que
A'Low designe l'indice le plus petit du tableau et A'High l'indice le
plus grand ca suffit?


Oui. Pour ce cas-ci, en tout cas. Mon expérience avec les langages de la
famille Pascal ne me permet pas à déviner ce que signifie l'opérateur '.


C'est un attribut. A'First (j'ai confondu avec VHDL qui a A'Low et
A'Left parce que les intervalles y sont directionnel) designe le
premier indice du tableau. Avec des attributs, tu peux aussi
recuperer le type de l'indice et d'autres choses interessantes.

A+

--
Jean-Marc
FAQ de fclc++: http://www.cmla.ens-cachan.fr/~dosreis/C++/FAQ
C++ FAQ Lite en VF: http://www.ifrance.com/jlecomte/c++/c++-faq-lite/index.html
Site de usenet-fr: http://www.usenet-fr.news.eu.org




Avatar
Michel Michaud
Dans news:,
Alexandre BACQUART wrote in message
news:<40e0516c$0$29365$...
C'est aussi une manière de
ne pas faire confiance au compilateur pour optimiser des
multiplications/divisions par des puissances de 2 en invoquant
soi-même l'opération de décalage (souvent un mnémonique dédiée
du processeur).


Sauf qu'il y a des processeurs où la multiplication est plus
rapide que le décalage, et où ce n'est pas le cas, le
compilateur en général sait mieux faire que toi.

On ne s'en sert jamais pour l'optimisation.


C'est un peu trop catégorique. J'ajouterais plutôt « aujourd'hui »
ou « probablement ». Mais anciennement, si ton compilateur ne
remplaçait pas une multiplication par un décalage et que ça avait
un impact important sur ton application, c'était utile de pouvoir
le faire explicitement dans ton langage évolué. C'est rare, mais ça
m'est déjà arrivé (en C)...

En fait, il est vrai qu'on parle ici de C++ alors tu as peut-être
raison de penser qu'aucun compilateur C++ n'a (jamais eu) besoin
d'aide pour bien multiplier par une puissance de 2... :-)

--
Michel Michaud
http://www.gdzid.com
FAQ de fr.comp.lang.c++ :
http://www.cmla.ens-cachan.fr/~dosreis/C++/FAQ/


Avatar
James Kanze
"Michel Michaud" writes:

|> Dans news:,
|> > Alexandre BACQUART wrote in message
|> > news:<40e0516c$0$29365$...
|> >> C'est aussi une manière de
|> >> ne pas faire confiance au compilateur pour optimiser des
|> >> multiplications/divisions par des puissances de 2 en invoquant
|> >> soi-même l'opération de décalage (souvent un mnémonique dédiée
|> >> du processeur).

|> > Sauf qu'il y a des processeurs où la multiplication est plus
|> > rapide que le décalage, et où ce n'est pas le cas, le
|> > compilateur en général sait mieux faire que toi.

|> > On ne s'en sert jamais pour l'optimisation.

|> C'est un peu trop catégorique. J'ajouterais plutôt « aujourd'hui »
|> ou « probablement ».

Tiens. Je croyais que « on ne s'en sert jamais » était au temps présent
en français. Je n'ai pas dit « on ne s'en servait jamais ». Encore
que...

|> Mais anciennement, si ton compilateur ne remplaçait pas une
|> multiplication par un décalage et que ça avait un impact important
|> sur ton application, c'était utile de pouvoir le faire explicitement
|> dans ton langage évolué. C'est rare, mais ça m'est déjà arrivé (en
|> C)...

Je ne l'ai vu qu'une fois. Je portais un programme au NSC 32000. Et on
avait des problèmes de performance (pas étonnant, avec ce processeur).
Grace au profiling, un des problèmes que j'ai trouvé, c'est qu'on
s'était servi des décalages à la place de la multiplication. Je les ai
remplacé par la multiplication, et ça allait déjàa plus vite. (Sur un
NSC 32000, la multiplication de deux entiers prenait un coup d'horloge.
Un décalage en prenait 2(n+1), où n était le nombre de places qu'on
décalait. Et quelqu'un avait optimisé la multiplication par 10 en
(n<<2+n)<<1.)

|> En fait, il est vrai qu'on parle ici de C++ alors tu as peut-être
|> raison de penser qu'aucun compilateur C++ n'a (jamais eu) besoin
|> d'aide pour bien multiplier par une puissance de 2... :-)

Je n'ai pas dit qu'on n'en a jamais eu besoin. Je dit qu'on n'a jamais
besoin. Aujourd'hui.

Je dirais plusieurs choses de plus : 1) il ne faut jamais le faire dans
le code réputé portable, 2) il ne faut jamais le faire sans faire du
profiling d'abord, et 3) en revanche, on pourrait y penser lors du choix
des constantes de multiplication, disons dans une fonction d'hachage --
on choisit une constante qui s'exprime facilement en termes de décalage,
au cas où.

--
James Kanze
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France +33 (0)1 30 23 00 34
Avatar
Gabriel Dos Reis
James Kanze writes:

[...]

| |> C'est un peu trop catégorique. J'ajouterais plutôt « aujourd'hui »
| |> ou « probablement ».
|
| Tiens. Je croyais que « on ne s'en sert jamais » était au temps présent
| en français. Je n'ai pas dit « on ne s'en servait jamais ». Encore
| que...

En fait, telle que tu l'as formulée, elle donne l'impression d'une
vérité immuable, au présent, comme au passé comme au future.

Je suis surpris que tu sois surpris.

-- Gaby
1 2 3 4