중급 예제

약간은 익숙하시거나 익숙해지셨나요? 그렇다면 조금더 깊이 다뤄볼까요?

2자리 이상의 숫자값 출력하기

2015-12-08 15:11:48

개요

 

실생활에서 쓰이는 문자는 분류하는 방법에 따라 여러가지로 나눌 수 있습니다.

 

제일 대표적인 것이 우리가 가장 많이 사용하는 언어가 있습니다.

이 언어중에는 한글을 비롯하여 영어, 일본어, 중국어, 프랑스어, 독일어, 에스파냐어 등의 다양한 형태가 존재합니다.

 

 

 

 

또 언어 뿐만 아니라 실생활에서는 숫자도 빠질 수 없는 문자죠!

 

 

 

언어와 숫자뿐만 아니라 각각의 기호들도 문자가 될 수 있습니다

 

.

 

 

특수 문자들도 역시 마찬가지죠~!

 

 

 

사람은 위의 언어, 숫자, 기호, 특수 문자 등을 보고 머리로 계산하여 각각을 구별할 수 있습니다.

 

하지만 컴퓨터의 경우에는 모든 데이터를 0또는 1의 2진수로 읽기 때문에 지금 받은 데이터가 어떤 형태의 값인지 구별이 불가능 합니다.

따라서 사람이 프로그래밍을 할때 임의적으로 이 데이터는 어떤 형태인지 선언을 하게 되는데 

 

아두이노 상에서 변수 앞에 붙이는 int나 char, boolean, String 등이 바로 이런것들 입니다.

하지만 한번 타입을 정한 변수라도 그 후에 타입이나 데이터 형태를 변경할 수 있습니다.

 

이번글에서는 아두이노IDE(스케치)에서 데이터 타입을 변환해보고 출력을 다양한 형태로 바꿔보겠습니다.

 

 

소프트웨어 Coding

 

1. 2자리 이상의 숫자값을 받아서 출력하기

 

시리얼통신을 사용한 데이터값 전송은 char나 unsigned char의 전송을 기본으로 하기 때문에 int값을 사용한 2자리 수 이상의 데이터값 전송이 까다로운 편입니다.

아래 사진과 같이 2자리수이상의 데이터를 입력하면 한글자씩 떨어져서 나오는 상황이 상당히 많습니다.

  

<56을 입력했지만 5와 6이 분리되는 위와 같은 상황이 상당히 빈번한 편이다>

 

char을 사용하여 데이터를 전송할 경우 1자리 값으로만 받기 때문에 배열을 사용해야 합니다. 

이때 atoi()함수를 사용하면 쉽게 char값을 int값으로 변환할 수 있습니다.

 

 

atoi(const char*);   // char형태의 데이터를 int데이터로 변환

 

 atoi()함수를 사용하여 2자리수의 int값을 출력해 봅시다.

char buffer[20];               //통신을 할때 buffer배열에 전송받은 데이터 입력
char bufferIndex = 0; 

void setup() {
  Serial.begin(9600);   //시리얼 통신 초기화
}


void loop() {
  while(Serial.available()) {
    buffer[bufferIndex]  = Serial.read();   //시리얼 통신으로 버퍼배열에 데이터 수신
    bufferIndex++;                          //데이터 수신 후 버퍼 인덱스 1 증가
  }         
  int pos = atoi(buffer);                   //atoi()함수로 char값을 int값으로 변환
  if(pos != 0) {
    Serial.print("Input data : ");
    Serial.println(pos);                    //int값으로 변환된 데이터 출력
    
    int plus = pos+50;    
    Serial.print("plus 50 : ");
    Serial.println(plus);                   //출력된 데이터에 50을 더하여 출력
    
  }
  delay(100); 
   
  //버퍼 초기화
  for(int a=0;a<21;a++) {
    buffer[a] = NULL;
  }
  bufferIndex = 0;
}

 

 

위의 소스를 사용할 경우 시리얼 모니터를 통해 입력된 데이터가 고스란히 시리얼 모니터 창에 뜨는 모습을 볼 수 있습니다.

응용할 수 있으면 블루투스를 이용하여 서보모터의 각도를 전송할 때, 온도센서, 습도센서의 값을 전송할 때 등 여러 가지로 사용이 가능합니다.

 

<제대로 2자리 수 이상의 int값을 출력한다>

 

 

 

2. 입력받은 숫자를 2진수, 10진수, 16진수로 표현하기

 

입력받은 데이터는 숫자일 경우 특별한 입력이 없는 경우 가장 기본적인 10진수로 출력이 됩니다.

하지만 어느 순간에는 2진수나, 16진수의 사용이 필요할때도 있습니다.

 

스케치에서 시리얼 모니터창에 출력하기 위한 함수는 Serial.print()이지만 이 매개변수 안에 값을 2개 넣어서 10진수를 2진수나, 16진수 혹은 16진수나 2진수를 10진수로 표현이 가능합니다.

 

Serial.println(data, BIN);   //data의 값을 2진수(Binary)로 출력
Serial.println(data, HEX);    //data의 값을 16진수(Hexadecimal)로 출력

 

위의 코드를 사용한다면 여러 데이터를 2진수나 16진수로 표현이 가능합니다.

1번의 코드에서 조금 더 추가해 이번에는 입력한 2자리 수 이상의 숫자를 2진수나 16진수로 받아보겠습니다.

 

char buffer[20];               //통신을 할때 buffer배열에 전송받은 데이터 입력
char bufferIndex = 0; 
char a = 'a';                  //char변수 a를 a로 지정

void setup() {
  Serial.begin(9600);   //시리얼 통신 초기화
}


void loop() {
  while(Serial.available()) {
    buffer[bufferIndex]  = Serial.read();   //시리얼 통신으로 버퍼배열에 데이터 수신
    bufferIndex++;                          //데이터 수신 후 버퍼 인덱스 1 증가
  }         
  int pos = atoi(buffer);                   //atoi()함수로 char값을 int값으로 변환
  if(pos != 0) {
    Serial.print("Input data : ");
    Serial.println(pos);                    //int값으로 변환된 데이터 출력
    
    Serial.print("Binary number : ");
    Serial.println(data, BIN);              //2진수로 변환된 데이터 출력
    
    Serial.print("Hexadecimal number : ");
    Serial.println(data, HEX);              //16진수로 변환된 데이터 출력

    Serial.print("Hexa char : ");javascript:void(0)
    Serial.println(a, HEX);                 //2진수로 변환된 char값 출력
  }
  delay(100); 
   
  //버퍼 초기화
  for(int a=0;a<21;a++) {
    buffer[a] = NULL;
  }
  bufferIndex = 0;
}

 

 

위의 코드를 실행하게 되면 아래와 같은 결과를 볼 수 있습니다.

첫 번째에 입력한 25의 2진수와 16진수를 볼 수 있고 int값 외에도 지정한 char변수 a에 대한 Hexa값 또한 확인이 가능합니다.

두 번째에도 역시 30에 대한 2진수와 16진수를 확인이 가능합니다.

 

 

 

16진수나 2진수에 대한 출력은 사실 그렇게 많이 쓰이지 않지만 알아두고 있으면 언젠간 써먹을일이 반드시 생깁니다!

사실 사용하는 방법도 어려운것이 없기 때문에 알아만 두셔도 됩니다.(알아서 손해보는 일은 없으니까요.)

 

하지만 1번에서와 같이 2자리 이상의 숫자값 전송같은 경우에는 아두이노간 통신, 블루투스를 이용한 통신 등에서 상당히 많이 쓰입니다.

byte로도 보낼 수 있지만 byte의 경우에는 1byte가 한정이기 때문에 255이상의 숫자는 사용이 불가능하다는 단점이 있습니다.

 

대표적인 경우가 서보모터의 각도를 제어할 때 저런 방식으로 보내면 그나마 쉽게 보낼 수 있습니다.

(저 방식을 몰라서 그냥 대충 'a'값 받아오고 'b'받아오고 이런 일이 상당히 흔하죠.)

kocoafabeditor

항상 진취적이고, 새로운 것을 추구하는 코코아팹 에디터입니다!

아두이노, 기타