LusoRobótica - Robótica em Português
Sistemas específicos => Arduino / AVR => Tópico iniciado por: pmj_pedro em 06 de Fevereiro de 2013, 00:41
-
Estou a corre este programa:
void setup(){
Serial.begin(57600);
}
void loop(){
long code = 0xFFFF;
byte n=32;
while( n>0 ){
if( (code & (1<<n)) != 0)
break;
n--;
}
Serial.print('\t');
Serial.print(n);
delay(1000);
}
Que deveria dizer o numero do bit em que acha o primeiro 1, mas ele so me diz para valores com menos de 16bits, eu compreendo como isto acontece, mas queria saber como posso por isto a funcionar
O resultado na consola
15 15 15 15 15 15 15
-
Experimenta fazer um cast da variavel n para long,e eu prefiro usar os designadores de variaveis diferentes, assim:
void setup(){
Serial.begin(57600);
}
void loop(){
int32_t code = 0xFFFF;
uint8_t n=32;
while( n>0 ){
if( (code & (1<<(int32_t)n)) != 0)
break;
n--;
}
Serial.print('\t');
Serial.print(n);
delay(1000);
}
E provavelmente será problema de variaveis com/sem sinal, e talvez atrofio do print.
-
Experimenta fazer um cast da variavel n para long,e eu prefiro usar os designadores de variaveis diferentes, assim:
void setup(){
Serial.begin(57600);
}
void loop(){
int32_t code = 0xFFFF;
uint8_t n=32;
while( n>0 ){
if( (code & (1<<(int32_t)n)) != 0)
break;
n--;
}
Serial.print('\t');
Serial.print(n);
delay(1000);
}
E provavelmente será problema de variaveis com/sem sinal, e talvez atrofio do print.
Continua sem funconiar e nao é problema do print
void setup(){
Serial.begin(57600);
}
void loop(){
int32_t code = 0xFFFF;
uint8_t n=32;
while( n>0 ){
if( (code & (1<<(int32_t)n)) != 0){
Serial.println(n);
break;
}
n--;
}
delay(1000);
}
Continua so a imprimir 15
-
Qual é a ideia mesmo?
Tira-lhe o break ver no que dá.
-
imprime de 15 a 1
Estou a ler um sensor que recebe um codigo, eu armazeno e depois quer testar desda posiçao 32 ate encontrar o primeiro 1, para testar o start bit
-
Bem este deixou-me curioso... :)
Após uns testes, já descobri o problema... (aliás problemas :P )
O primeiro está na linha:
if( (code & (1<<n)) != 0)
Aquele 1, como não foi dito nada em contrário, é um int de 16 bits, logo não serve...
Na mesma linha, esquecendo o detalhe dos 16 bits, o shift maior deveria ser <<31 e não <<32, pois o 1 inicial está já no 1º bit, logo so tem de andar 31x.
E por ultimo, mas não menos importante... Algo que nenhum de nós reparou e tava mmo á vista...
0xFFFF são só 2 bytes... :P Logo precisas de 0xFFFFFFFF.
Portanto precisas de algo do tipo:
unsigned long code = 0xFFFFFFFF;
byte n=32;
while( n>0 ){
Serial.println(((unsigned long)1<<(n-1)), BIN);
if( (code & ((unsigned long)1<<(n-1))) != 0)
break;
n--;
}
Serial.print('\t');
Serial.print(n);
-
Espetaculo, ja funciona
O numero de deslcomaneto ja tinham reparado que era 32, mas depois quando quis alterar isso para sizeof(long)-1, vi que nada alterava e voltei eu a escrever o numero, obrigado por esse reparo
Estava com medo que tivesse que deparar o long em byte e fazer byte a byte o shift, mas assim funciona
Obgd
-
Pois é, esqueci-me que o 1 tambem tem de levar cast, basta meteres assim:
1UL
-
Olha essa sintaxe n conhecia... :)
-
Não é ANSI C, logo funciona no avr-gcc por causa de defines que ele tem lá no inttypes e isso, não é algo universal.
-
Eu tenho a impressão que já vi isso quando se define a frequência do arduino
-
Sim, tipo isto:
#define F_CPU 16000000UL
-
Boas,
Por essas e por outras é que as constantes numéricas que envolvam manipulação de bits devem ser sempre
expressas em hexa com a dimensão (word, dword, qword) que a variável de referencia, ex: 0x00000001 << n-1
como a subtracção (neste caso "n-1") tem precedência sobre o bitwise nem sequer é necessário parêntesis.
Abraços,
PA
-
Boas,
Por essas e por outras é que as constantes numéricas que envolvam manipulação de bits devem ser sempre
expressas em hexa com a dimensão (word, dword, qword) que a variável de referencia, ex: 0x00000001 << n-1
como a subtracção (neste caso "n-1") tem precedência sobre o bitwise nem sequer é necessário parêntesis.
Abraços,
PA
Quando trabalhava com um pic32, para mim fazia sentido usar, mas depois quando se trabalha com atmega 8bits, acho que nao é assim tao importante
Mas tb so nao uso mais, pk ainda nao tenho mt bem assimilado o binario e o hexadecimal