Aller au contenu


Photo
- - - - -

arduino - interface user


  • Veuillez vous connecter pour répondre
3 réponses à ce sujet

#1 philouxy

philouxy

    Membre

  • Membres
  • 50 messages
  • Gender:Male
  • Location:Riviera Vaudoise - Suisse

Posté 27 janvier 2015 - 05:24

Bonjour à tous,

Me revoici avec mes problèmes existentielles avec cette petite board ARDUINO. => suis toujours entrain d'améliorer mon Test Bench (voir discussion : http://www.robot-maker.com/forum/topic/9774-arduino-et-ic-ic-cdp68hc68p1/)

ici je veux simplement remplir un tableau avec 256 cases de 0 à 255, voir le code ci-dessous:


unsigned int i; char tb_ref[256];....  for(i = 0; i <= 0xFF ; i++)  {    tb_ref[i] = i;    Serial.println(tb_ref[i], DEC);   }....
Mais comme on peut le constater sur l'image ci-dessous :

150127052210830141.png

à un moment donné je passe en valeur négative, est-ce simplement une erreur d'affichage ?

Comme d'habitude si vous avez des infos, suggestions, solutions, ou autres, je suis preneur

Amicalement - Philou

-------------------------------------

Amicalement le cht'y Philou

 

Fixme Members : fixme.ch
-------------------------------------


#2 R1D1

R1D1

    Modérateur et Membre passionné

  • Modérateur
  • PipPipPipPipPip
  • 1 211 messages
  • Gender:Male
  • Location:Autriche

Posté 27 janvier 2015 - 06:01

Salut ! Le problème est assez simple : le char en arduino encode des valeurs sur 8 bits de 127 à -128. Comme ton unsigned int parcourt bien de 0 à 255, il y a dépassement de la capacité limite du char, et comportement non défini de la variable, même si l'implémentation la plus courante est de prendre le complément à deux. Réfs : http://arduino.cc/en/Reference/Char http://arduino.cc/en/Reference/UnsignedChar
R1D1 - Calculo Sed Ergo Sum -- en ce moment, M.A.R.C.E.L.
Avatar tiré du site bottlebot

#3 philouxy

philouxy

    Membre

  • Membres
  • 50 messages
  • Gender:Male
  • Location:Riviera Vaudoise - Suisse

Posté 28 janvier 2015 - 09:24

Bonsoir à tous,

 

Merci à toi R1D1 pour ces explications, effectivement j'ai mis toutes mes valeurs en "en unsgined char", ca fonctionne mieux :Koshechka_08: 

amicalement - Philou  


-------------------------------------

Amicalement le cht'y Philou

 

Fixme Members : fixme.ch
-------------------------------------


#4 cocothebo

cocothebo

    Membre passionné

  • Membres
  • PipPipPip
  • 341 messages
  • Gender:Male

Posté 28 janvier 2015 - 09:45

Salut,

 

C'est effectivement un problème classique que l'on rencontre quand on utilise des valeurs signées et non signées en même temps et sans en tenir compte...

 

Par contre techniquement parlant il n'y a pas de "dépassement" ou autre d'un char, je m'explique!

Pour commencer même si on parle de valeur signée ou non, en vrai en informatique la notion n'existe pas (c'est juste une abstraction rajoutée), les registres ou autres ont juste des valeurs binaires composées donc d'un ensemble de 1 ou 0 mais il n'y a pas de notion de négatif ou positif.

 

bref pour reprendre l'exemple,

la valeur de i est un unsigned int, donc une valeur codée sur 2 ou 4 octets (ça dépend de l'arduino utilisé), prenons 2 octets pour l'exemple.

Notre i va varier de 00000000 00000000b à 00000000 11111111b

cette variable est mise dans un char codé sur un octet ce qui nous fait qu'en fait on tronque l'int de son octet de poids fort pour garder que le deuxième (poids faible)

Ce tableau aura donc en

première "case"     (00000000) 00000000b (partie tronquée entre parenthèses)

deuxième "case"    (00000000) 00000001b

...

127eme case         (00000000) 01111111b

128eme case         (00000000) 10000000b

129eme case         (00000000) 10000001b

...

255eme case         (00000000) 11111110b

256eme case         (00000000) 11111111b

 

 

On voit donc que aucun dépassement n'est arrivé (mis a par le passage int en char mais l'octet de poids fort est toujours à 0), en revanche puisque tu as déclaré un "char" qui est officiellement signé, ta fonction de print va essayer de réaliser l'abstraction du signe qui est basiquement le premier bit d'une valeur signée est le  signe, si c'est un 0 c'est positif si c'est un 1 c'est négatif.

C'est pourquoi l'affiche jusque la 127eme case reste "normale", le char commence par 0, donc on l'affiche comme du positif

A partir de la 128eme case, le premier bit passant à 1, il est considéré négatif, et donc la fonction print va envoyer la représentation du contenu de cette case en négatif

 

 

 

Toussa pour dire que ce comportement n'est pas du tout inattendu et n'est juste que la représentation finale qui est réalisée en utilisant un mauvaise "encodage" (comme si tu veux afficher un texte encodé en Unicode en le décodant avec du ISO 8859, le texte ne sera pas lisible directement, même si le contenu de ton fichier n'est en fait pas changé)

 

 

 

 

Pour le code en lui même, il est plutôt conseiller d'utiliser le type byte pour des valeurs non signées sur un octet (à la place de unsigned char) même si le résultat sera le même. De même stocker une valeur codée sur plus d'octets que celle de stockage (ici mettre un int dans un byte) amène très souvent à des gros problèmes (pas le cas ici) puisque qu'en tronquant les valeurs, tu vas réduire la plage de valeur possibles et avoir des "bouclages".

 

 

Cordialement






0 utilisateur(s) li(sen)t ce sujet

0 members, 0 guests, 0 anonymous users