', { cookie_domain: 'auto', cookie_flags: 'max-age=0;domain=.tistory.com', cookie_expires: 7 * 24 * 60 * 60 // 7 days, in seconds }); 'Making' 카테고리의 글 목록 (3 Page) :: MakerLee's Workspace
728x90

딱 한번 크림납을 사용해 봤지만 그 편리성에 반했습니다. 

꼭 스텐실을 사용하지 않더라도 제가 SMD 작업을 많이 하는 이상 크림납 작업을 하는게 많이 편리할 것 같더군요. 

 

하지만 일반 주사기를 손으로 제어해서 크림납을 정량으로 압출하는 것은 매우 힘이 듭니다. 

 

 

 

 

 

그래서 알아보니 이런 물건이 있더군요. 

한 50년대쯤 개발된 물건 같은데 원리는 간단합니다. 

공기압력을 일정시간 ON/OFF 해서 조금씩 주사기를 밀어내는거죠. 

액체의 점도에 따라 공기압은 수동으로 조절하고요. 

당연하게도 저걸 사용하려면 컴프레서가 따로 필요합니다. 

뭐 이런 무식한 기계를 지금까지 쓰고 있나 싶습니다. 

 

 

 

 

 

 

 

https://www.i-extruder.com/

대체할 물건을 찾다가 킥스타터에서 봤던 물건이 생각나서 찾아봤습니다.

펀딩에는 실패한 것으로 기억하는데 그래도 제품은 판매를 하는군요.

주사기를 내부에 넣고 스위치를 누를때마다 뒤에서 모터가 조금씩 밀어주면 되는 시스템입니다. 

 

 

 

 

자세한 내용은 동영상 참조. 

 

 

 

 

 

 

 

비슷한 생각을 저만 한 것은 아닌지 이런 물건을 만든 분도 있더군요. 

 

 

 

 

 

 

 

일단은 한 손에 들수 있는 모양이 나을 것 같아 이쪽으로 설계를 하는 중입니다. 

보드는 아두이노 나노 보드가 들어갈 수 있을 것 같긴 한데 사이즈가 모자라면 따로 보드를 제작해야 할 것 같네요

 

 

 

 

 

 

일부만 출력해서 스위치 누름에 문제가 없는지 테스트 중입니다. 

 

 

 

 

 

주문한 모터가 도착하면 본격적으로 테스트를 해 볼 생각입니다. 

728x90
728x90

오래전에 킥스타터에 이런 물건이 올라왔습니다. 

저는 이것을 보는 순간 옆의 LED가 RGB VU미터일거라고 생각하고 완성되면 어떤 모습일지 기대를 했습니다.

하지만 그냥 색이 약간 변하는 LED일 뿐이더군요. 

 

 

 

 

매우 비싼 아날로그 VU미터 헤드폰

고양이 귀는 필요없지만 LED VU 미터가 달린 헤드폰이라면 갖고 싶었는데 딱히 그런 물건은 나오질 않더군요. 

그래서 한번 만들어 볼까 하는 생각이 들었습니다. 

 

 

 

 

 

 

 

헤드밴드를 3D 프린터로 출력할 수 있을지 의문이 가서 간단한 형태를 만들어 봤습니다. 

두께를 조절하면 적당한 탄성으로 사용할 수 있을 것 같더군요. 

 

 

 

 

 

 

 

 

 

알리에서 헤드폰 모듈과 이어컵 스폰지를 구매했습니다. 

아직 헤드폰 앰프 모듈은 도착하지 않았습니다. 

이런 부품들을 알리에서 구할 수 있으니 여러모로 취미생활에 참 많은 도움이 됩니다. 

 

 

 

 

 

 

 

이어컵을 끼울 수 있는 간단한 형태를 만들어봤습니다. 

이 부분은 별 무리가 없겠네요

 

 

 

헤드폰 앰프 모듈이 도착하면 회로를 고민해 봐야 할 것 같습니다.

단순히 스테레오 연결로 만들게 되면 그나마 간단하게 끝날 것 같은데

블루투스를 넣어야 한다면 많이 복잡해 질 것 같네요. 

 

 

728x90
728x90

일단은 MCP4725 소자와 ADS1115소자를 테스트하기 위한 예제코드를 넣어봤습니다. 

 

 

 

ADS1115 예제 코드에서 0번 채널은 제대로 센싱을 하는데 1번 채널이 동작을 하지 않네요

2, 3번 채널도 정상동작합니다.

단지 1번 채널만 동작을 하지 않는군요. 

그리고 그 채널은 하필 제가 쓰는 2개의 채널중 하나입니다. 

힘들게 떼어내고 다시 납땜을 했습니다. 

 

 

 

외부전원만 들어가면 시리얼값이나 측정값이 미쳐 날뜁니다. 

저 DC-DC 강압회로는 싼값에 사서 넣어봤는데 전원노이즈가 엄청 심하더군요.

 

 

 

 

 

 

제거하고 다른 강압회로로 교체했습니다. 

 

 

 

 

 

 

 

 

코드를 다시 수정해서 일단 2개 채널을 정상적으로 나오게 하고 배터리를 끼워보며 전압을 확인해 봤습니다. 

정상적으로 나오나 싶더니 어느 순간부터 이상하게 됩니다. 

2번 배터리 홀더에 넣으면 정상적으로 3.61V 전압이 나오는데 

1번 배터리 홀더에 넣으면 1.92V 가 나옵니다. 

 

ADS1115칩이 또 나갔나 싶긴 한데 저 깨알같은 걸 다시 재납땜하자니 걱정이네요

슬슬 PCB 패턴이 일어날것도 같고 문제생길 때마다 회로를 다시 납땜하기도 힘들 것 같습니다. 

 

 

 

 

 

작게 만든다고 노력을 했는데 그냥 모듈로 교체해야 겠습니다. 

다시 PCB부터 떠야겠네요

728x90
728x90

회로를 짰습니다. 

비용절감하느라 100*100 안에 어떻게든 다 집어넣느라 힘드네요.

 

 

 

제 케릭터를 한번 집어넣어봤습니다만

 

 

 

 

 

 

생각없이 흰색 PCB로 주문하는 바람에 망했습니다. 

그리고 크기도 너무 작네요. 

 

 

 

 

 

 

방전률을 담당하는 ADC(MCP4725)는 그럭저럭 괜찮습니다.

하지만 전압체크를 담당하는 DAC(ADS1115)는 핀이 SOP10패키지라 납땜이 쉽지 않더군요. 

 

 

 

 

 

 

728x90
728x90


배터리 내부저항 측정기의 구조는 배터리의 전압을 측정 후에

다시 배터리에 아주 낮은 값의 저항을 연결하고 전압을 측정해서 계산을 통해 내부 저항을 계산하게 됩니다. 

 

이를 자동으로 구현하려면 당연히 ON/OFF를 담당하는 FET 가 필요하게 되고요. 

여기서 FET를 계속 켜 놓으면 방전이 계속되므로  배터리 방전기가 되겠죠.

 

이렇게 배터리 테스터를 방전기로 사용할 수 있게 됩니다.

 

이때 FET를 그냥 작동시키는게 아니라 OPAMP를 통해서 비교전압을 걸어주면 정전류로 방전을 할 수 있습니다. 

https://www.youtube.com/watch?v=8uBcywBUTkw&t=6s
(참조)

그러면 이제 배터리 내부저항 체크와 정전류 방전을 통해 배터리의 용량체크까지 할 수 있게 됩니다. 

https://cafe.naver.com/hssoon/207863 

 

[ 왕초보의 ] 좌충우돌.... 자작...

[ 왕초보의 ] 좌충우돌.... 자작 방전기 제작기 ( 방전기시리즈 최종회 ) ...

cafe.naver.com

그런데 이렇게 아이디어를 짜 놓고 보니 위와 같이 어느분이 이미 만들어 놓으셨더군요.. 

 

 

 

 

핵심 회로는 간단합니다. 

아두이노 핀이 많이 남아서 채널수를 늘리고 싶기도 한데

MCP4725(I2C DAC)은 i2c 주소 2개가 한계라 더이상 달수가 없군요. 

 

728x90
728x90

0.9" OLED를 썼을 때는 괜찮은데 1.3" OLED를 사용하면 위와 같이 오른쪽에 두줄이 노이즈처럼 켜집니다. 

어떻게 해야되는지 몰라서 그냥 썼습니다만 검색해 보니 의외로 쉽게 답이 있군요






라이브러리 폴더 안의 U8Glib\src\clib\u8g_dev_ssd1306_128x64.c 파일을 열어서 0x000을 0x002로 수정해 주면 된다고 합니다. 








업데이트 이후로는 라이브러리 폴더가 아두이노 설치폴더가 아니라 C:\user\documents\arduino 아래 폴더로 옮겨졌습니다. 





해당 파일을 찾아 수정했습니다. 







깨끗하게 잘 나오는군요


728x90
728x90

잘 쓰다가 떨어져서 고장났네요. 

수리하면서 이참에 제대로 완성시켜볼까 합니다. 







핀을 몇개 안 쓰기 때문에 Attiny85 를 쓰도록 설계해봤습니다. 








보드도 다시 짰습니다. 테스트용 보드를 하나 만들어 보고 싶은데 CNC도 컨트롤부 전부 바꾸려고 뜯어놓은 상태라

이대로 PCB 주문할지 말지 생각중입니다. 


728x90
728x90

BigNumber는 큰 수 처리에 정말 좋은 라이브러리지만 

초보자를 위한 라이브러리는 아닌 듯.



참조1)

loop 바깥에서

BigNumber a="1234567890.0987654321"; 로 전역선언후 시리얼로 출력해 보면

a=1234567890

로 나온다. 


BigNumber a=1234567890.0987654321; 로 따옴표를 떼면

a=32767로 나옴. 



특이하게도 

BigNumber a='1234567890.0987654321'; 로 홑따옴표를 붙이면

a=12849가 된다. 


BigNumber a="1234567890.0987654321"; 를 loop 안쪽에서 선언하면 

a=1234567890.0987654321 로 제대로 나온다.



BigNumber a = "123556.2342" 형태나 BigNumber a ("143563245.21345245") 형태로 사용해야 한다. 

이 라이브러리는 숫자를 String 취급하는 것 같은데 

그렇다고 실제로 String으로 생각하고 스케치를 하면 오류를 뿜는다. 

문자열 길이를 측정하는 length() 같은 함수를 쓸 수 없다. 




참조2)

LED 디스플레이에 숫자 표기를 정확히 하기 위해서는 숫자의 자리수가 얼마인지 셀 수 있어야 한다.

디스플레이의 자릿수를 벗어나면 정리해 주어야 한다.


숫자의 길이를 측정하려면 
char s = n.toString();  //n을 문자열로 치환하여 s에 저장

length = strlen(s);        //s의 길이를 구하여 length에 저장

같은 식으로 사용해야 한다. 


하지만 이 경우 소수점이 포함되어 계산되므로 

1 -> 1자리수

1.00 -> 4자리수 로 계산되는 문제가 있다.



문제1)

1이상의 수는 어떻게든 처리가 가능하다.

하지만 1 미만의 수는 소수점 때문에 처리가 매우 곤란해진다. 

1 = 1.0000000 과 같이 나오는데 이 경우 0.000000을 어떻게 처리해야 하는가?


문제2)

소수점 이하의 수는 자리수를 어떻게 계산하는가?

1 이상의 수는 10씩 나눠가면서 그 수가 0보다 큰지 아닌지 체크하고
0보다 크면 다시 10 나누는 식으로 자릿수를 계산할 수 있다.

456 
10을 나눈다. = 45.6   (1회)
1보다 큰가? ->yes
10을 나눈다 = 4.56    (2회)
1보다 큰가? ->yes
10을 나눈다 = 0.456  (3회)
1보다 큰가? ->no

3회 반복했으므로 자릿수는 3

하지만 1보다 작은 수는 어떻게 처리해야 하는가?
ex)0.000123


추측1)

123.456을 123 과 0.456으로 분리할 수 있다면 위의 문제들을 해결하기 쉬울 것 같다.
분리하는 방법은?



http://cafe.naver.com/arduinostory/52325


https://arduino.stackexchange.com/questions/1013/how-do-i-split-an-incoming-string



http://cafe.naver.com/arduinostory/27858


728x90
728x90



숫자를 입력할 때마다 한자리씩 늘어나므로 

LED 디스플레이의 커서 위치는 한자리씩 이동해야 합니다. 


length() 함수를 이용해서 커서 위치를 계산해 표시하도록 했습니다.

그랬더니 일정 자릿수가 넘어가면 자릿수가 엉뚱하게 0이 되더군요.

모니터링을 해 봤더니 string 형식의 범위를 벗어나는 문제였습니다. 

BigNumber 사용하느라 생각을 못 했는데 이것도 어찌보면 당연히 발생되는 문제죠.



추가로 생각을 하다 보니 134123456.134526 같이 소수점 자리수가 늘어나면 그에 대한 처리도 해야 합니다. 

숫자를 제대로 체크하려면 BigNumber 함수에서 소수점 이하 자리수를 정확하게 알아야 합니다. 

BigNumber::setScale(3) 으로 하면 100 이 100.000으로 표시됩니다. 



한참 고민을 하다가 자리수를 계산하는 별도의 함수를 만들면 된다는 생각이 들었습니다. 

12341234 를 10씩 나눠가면서 1보다 크거나 같은지 계산하고

1보다 작아지는 순간 이 과정을 몇번 반복했는지 체크하면 자리수를 알아낼 수 있습니다.

반면 소수점 이하 자리수는 이렇게 체크할 수가 없습니다. 

어찌어찌 하면 될 것 같은데.. 머리속에서 맴돌기만 하고 구체화가 안되네요.

이건 조금 더 고민해 봐야겠습니다. 












Grang Total, MR, +-*/ 등의 일반 계산기에서 보여주는 표시를

LED로 표시하도록 했습니다. 

5개의 핀으로 끝내려 했는데 Low BAT 표시등도 넣어야 해서 

6개의 핀으로 3*3 매트릭스를 만들려고 테스트해봤습니다. 


사칙연산 표시는 그냥 디스플레이에 같이 표기해도 되는지라 LED를 넣을지 뺄지 생각중입니다. 

728x90
728x90


VR 기기를 구매해서 한동안 빠져 살았습니다. 

오랫동안 갖고 싶었던 기계인데 너무 비싸서 구매를 주저하고 있었죠.

블프 세일때 저렴하게 올라와서 구매를 결정했습니다. 










그래도 최근 며칠간은 계산기 스케치를 다시 파고들었습니다. 아주 조금이지만요.

BigNumber 라이브러리와 LedDisplay 라이브러리를 조합해서 쓰려니 자료형과 변수형이 머릿속에서 마구 꼬입니다.






키패드 누르는 대로 첫번째 숫자가 자릿수 올라가며 디스플레이되고 있습니다. 

겨우 한걸음 떼었네요 

728x90
728x90

아두이노에서 10여자리 이상의 큰 수나 소수점 이하의 수를 처리하는 문제는

며칠간의 공부 끝에 내 능력으로는 힘들겠구나 하고 결론을 내렸습니다;


그래서 계속 구글링을 했는데 며칠간의 검색 끝에 결국 괜찮은 라이브러리를 찾았습니다.

https://github.com/nickgammon/BigNumber


BigNumber.zip


원문 도큐먼트가 개발자 개인 블로그 에 있길래 혹시 사라질 지 몰라 카피했습니다. 

일단 예문과 결과값을 보면 제가 원하는 부분을 확실히 해결해 줄 수 있을 듯 합니다. 


우린 답을 찾을 것이다. 늘 그랬듯이. 구글에서.


 

Posted byNick Gammon   Australia  (21,293 posts)  [Biography] bio   Forum Administrator
DateTue 31 Jan 2012 09:00 PM (UTC)

Amended on Sat 23 Aug 2014 03:49 AM (UTC) by Nick Gammon

Message
I love big numbers ... they are so ... big!

So in the spirit of getting your Arduino to handle nice, big, numbers I have ported (with pretty minimal effort on my part) the GNU "bc" library to an Arduino library. This can be downloaded from:

http://www.gammon.com.au/Arduino/BigNumber.zip

Just unzip into your "libraries" folder.

Also now available from GitHub:

https://github.com/nickgammon/BigNumber

Factorials


Example sketch:


// BigNumber test: factorials
#include "BigNumber.h"

// function to display a big number and free it afterwards
void printBignum (BigNumber & n)
{
  char * s = n.toString ();
  Serial.println (s);
  free (s);
}  // end of printBignum

void setup ()
{
  Serial.begin (115200);
  Serial.println ();
  BigNumber::begin ();  // initialize library
 
  //factorials
  BigNumber fact = 1;

  for (int i = 2; i <= 200; i++)
  {
    Serial.print (i);
    Serial.print ("! = ");
    fact *= i;
    printBignum (fact);
  }

}  // end of setup

void loop () { }



Output from above:


2! = 2
3! = 6
4! = 24
5! = 120
6! = 720
7! = 5040
8! = 40320
9! = 362880
10! = 3628800
11! = 39916800
12! = 479001600
13! = 6227020800
14! = 87178291200
15! = 1307674368000
16! = 20922789888000
17! = 355687428096000
18! = 6402373705728000
19! = 121645100408832000
20! = 2432902008176640000
21! = 51090942171709440000
22! = 1124000727777607680000
23! = 25852016738884976640000
24! = 620448401733239439360000
25! = 15511210043330985984000000
26! = 403291461126605635584000000
27! = 10888869450418352160768000000
28! = 304888344611713860501504000000
29! = 8841761993739701954543616000000
30! = 265252859812191058636308480000000
31! = 8222838654177922817725562880000000
32! = 263130836933693530167218012160000000
33! = 8683317618811886495518194401280000000
34! = 295232799039604140847618609643520000000
35! = 10333147966386144929666651337523200000000
36! = 371993326789901217467999448150835200000000
37! = 13763753091226345046315979581580902400000000
38! = 523022617466601111760007224100074291200000000
39! = 20397882081197443358640281739902897356800000000
40! = 815915283247897734345611269596115894272000000000
41! = 33452526613163807108170062053440751665152000000000
42! = 1405006117752879898543142606244511569936384000000000
43! = 60415263063373835637355132068513997507264512000000000
44! = 2658271574788448768043625811014615890319638528000000000
45! = 119622220865480194561963161495657715064383733760000000000
46! = 5502622159812088949850305428800254892961651752960000000000
47! = 258623241511168180642964355153611979969197632389120000000000
48! = 12413915592536072670862289047373375038521486354677760000000000
49! = 608281864034267560872252163321295376887552831379210240000000000
50! = 30414093201713378043612608166064768844377641568960512000000000000
51! = 1551118753287382280224243016469303211063259720016986112000000000000
52! = 80658175170943878571660636856403766975289505440883277824000000000000
53! = 4274883284060025564298013753389399649690343788366813724672000000000000
54! = 230843697339241380472092742683027581083278564571807941132288000000000000
55! = 12696403353658275925965100847566516959580321051449436762275840000000000000
56! = 710998587804863451854045647463724949736497978881168458687447040000000000000
57! = 40526919504877216755680601905432322134980384796226602145184481280000000000000
58! = 2350561331282878571829474910515074683828862318181142924420699914240000000000000
59! = 138683118545689835737939019720389406345902876772687432540821294940160000000000000
60! = 8320987112741390144276341183223364380754172606361245952449277696409600000000000000
61! = 507580213877224798800856812176625227226004528988036003099405939480985600000000000000
62! = 31469973260387937525653122354950764088012280797258232192163168247821107200000000000000
63! = 1982608315404440064116146708361898137544773690227268628106279599612729753600000000000000
64! = 126886932185884164103433389335161480802865516174545192198801894375214704230400000000000000
65! = 8247650592082470666723170306785496252186258551345437492922123134388955774976000000000000000
66! = 544344939077443064003729240247842752644293064388798874532860126869671081148416000000000000000
67! = 36471110918188685288249859096605464427167635314049524593701628500267962436943872000000000000000
68! = 2480035542436830599600990418569171581047399201355367672371710738018221445712183296000000000000000
69! = 171122452428141311372468338881272839092270544893520369393648040923257279754140647424000000000000000
70! = 11978571669969891796072783721689098736458938142546425857555362864628009582789845319680000000000000000
71! = 850478588567862317521167644239926010288584608120796235886430763388588680378079017697280000000000000000
72! = 61234458376886086861524070385274672740778091784697328983823014963978384987221689274204160000000000000000
73! = 4470115461512684340891257138125051110076800700282905015819080092370422104067183317016903680000000000000000
74! = 330788544151938641225953028221253782145683251820934971170611926835411235700971565459250872320000000000000000
75! = 24809140811395398091946477116594033660926243886570122837795894512655842677572867409443815424000000000000000000
76! = 1885494701666050254987932260861146558230394535379329335672487982961844043495537923117729972224000000000000000000
77! = 145183092028285869634070784086308284983740379224208358846781574688061991349156420080065207861248000000000000000000
78! = 11324281178206297831457521158732046228731749579488251990048962825668835325234200766245086213177344000000000000000000
79! = 894618213078297528685144171539831652069808216779571907213868063227837990693501860533361810841010176000000000000000000
80! = 71569457046263802294811533723186532165584657342365752577109445058227039255480148842668944867280814080000000000000000000
...



Powers



// BigNumber test: powers
#include "BigNumber.h"

// function to display a big number and free it afterwards
void printBignum (BigNumber & n)
{
  char * s = n.toString ();
  Serial.println (s);
  free (s);
}  // end of printBignum


void setup ()
{
  Serial.begin (115200);
  Serial.println ();
  BigNumber::begin ();  // initialize library

  Serial.println ("--- powers of 2 ---");
  
  BigNumber a = 2;

  for (int i = 1; i <= 300; i++)
  {
    Serial.print ("2^");
    Serial.print (i);
    Serial.print (" = ");
    BigNumber p = a.pow (i);
    printBignum (p);
  }  // end of for loop

  Serial.println ("--- powers of 3 ---");
  
  a = 3;

  for (int i = 1; i <= 300; i++)
  {
    Serial.print ("3^");
    Serial.print (i);
    Serial.print (" = ");
    BigNumber p = a.pow (i);
    printBignum (p);
  }  // end of for loop

}  // end of setup

void loop () { }


Output from above:


--- powers of 2 ---
2^1 = 2
2^2 = 4
2^3 = 8
2^4 = 16
2^5 = 32
2^6 = 64
2^7 = 128
2^8 = 256
2^9 = 512
2^10 = 1024
2^11 = 2048
2^12 = 4096
2^13 = 8192
2^14 = 16384
2^15 = 32768
2^16 = 65536
2^17 = 131072
2^18 = 262144
2^19 = 524288
2^20 = 1048576
2^21 = 2097152
2^22 = 4194304
2^23 = 8388608
2^24 = 16777216
2^25 = 33554432
2^26 = 67108864
2^27 = 134217728
2^28 = 268435456
2^29 = 536870912
2^30 = 1073741824
2^31 = 2147483648
2^32 = 4294967296
2^33 = 8589934592
2^34 = 17179869184
2^35 = 34359738368
2^36 = 68719476736
2^37 = 137438953472
2^38 = 274877906944
2^39 = 549755813888
2^40 = 1099511627776
2^41 = 2199023255552
2^42 = 4398046511104
2^43 = 8796093022208
2^44 = 17592186044416
2^45 = 35184372088832
2^46 = 70368744177664
2^47 = 140737488355328
2^48 = 281474976710656
2^49 = 562949953421312
2^50 = 1125899906842624
2^51 = 2251799813685248
2^52 = 4503599627370496
2^53 = 9007199254740992
2^54 = 18014398509481984
2^55 = 36028797018963968
2^56 = 72057594037927936
2^57 = 144115188075855872
2^58 = 288230376151711744
2^59 = 576460752303423488
2^60 = 1152921504606846976
2^61 = 2305843009213693952
2^62 = 4611686018427387904
2^63 = 9223372036854775808
2^64 = 18446744073709551616
2^65 = 36893488147419103232
2^66 = 73786976294838206464
2^67 = 147573952589676412928
2^68 = 295147905179352825856
2^69 = 590295810358705651712
2^70 = 1180591620717411303424
2^71 = 2361183241434822606848
2^72 = 4722366482869645213696
2^73 = 9444732965739290427392
2^74 = 18889465931478580854784
2^75 = 37778931862957161709568
2^76 = 75557863725914323419136
2^77 = 151115727451828646838272
2^78 = 302231454903657293676544
2^79 = 604462909807314587353088
2^80 = 1208925819614629174706176
2^81 = 2417851639229258349412352
2^82 = 4835703278458516698824704
2^83 = 9671406556917033397649408
2^84 = 19342813113834066795298816
2^85 = 38685626227668133590597632
2^86 = 77371252455336267181195264
2^87 = 154742504910672534362390528
2^88 = 309485009821345068724781056
2^89 = 618970019642690137449562112
2^90 = 1237940039285380274899124224
2^91 = 2475880078570760549798248448
2^92 = 4951760157141521099596496896
2^93 = 9903520314283042199192993792
2^94 = 19807040628566084398385987584
2^95 = 39614081257132168796771975168
2^96 = 79228162514264337593543950336
2^97 = 158456325028528675187087900672
2^98 = 316912650057057350374175801344
2^99 = 633825300114114700748351602688
2^100 = 1267650600228229401496703205376
2^101 = 2535301200456458802993406410752
2^102 = 5070602400912917605986812821504
2^103 = 10141204801825835211973625643008
2^104 = 20282409603651670423947251286016
2^105 = 40564819207303340847894502572032
2^106 = 81129638414606681695789005144064
2^107 = 162259276829213363391578010288128
2^108 = 324518553658426726783156020576256
2^109 = 649037107316853453566312041152512
2^110 = 1298074214633706907132624082305024
2^111 = 2596148429267413814265248164610048
2^112 = 5192296858534827628530496329220096
2^113 = 10384593717069655257060992658440192
2^114 = 20769187434139310514121985316880384
2^115 = 41538374868278621028243970633760768
2^116 = 83076749736557242056487941267521536
2^117 = 166153499473114484112975882535043072
2^118 = 332306998946228968225951765070086144
2^119 = 664613997892457936451903530140172288
2^120 = 1329227995784915872903807060280344576
2^121 = 2658455991569831745807614120560689152
2^122 = 5316911983139663491615228241121378304
2^123 = 10633823966279326983230456482242756608
2^124 = 21267647932558653966460912964485513216
2^125 = 42535295865117307932921825928971026432
2^126 = 85070591730234615865843651857942052864
2^127 = 170141183460469231731687303715884105728
2^128 = 340282366920938463463374607431768211456
2^129 = 680564733841876926926749214863536422912
2^130 = 1361129467683753853853498429727072845824
2^131 = 2722258935367507707706996859454145691648
2^132 = 5444517870735015415413993718908291383296
2^133 = 10889035741470030830827987437816582766592
2^134 = 21778071482940061661655974875633165533184
2^135 = 43556142965880123323311949751266331066368
2^136 = 87112285931760246646623899502532662132736
2^137 = 174224571863520493293247799005065324265472
2^138 = 348449143727040986586495598010130648530944
2^139 = 696898287454081973172991196020261297061888
2^140 = 1393796574908163946345982392040522594123776
2^141 = 2787593149816327892691964784081045188247552
2^142 = 5575186299632655785383929568162090376495104
2^143 = 11150372599265311570767859136324180752990208
2^144 = 22300745198530623141535718272648361505980416
2^145 = 44601490397061246283071436545296723011960832
2^146 = 89202980794122492566142873090593446023921664
2^147 = 178405961588244985132285746181186892047843328
2^148 = 356811923176489970264571492362373784095686656
2^149 = 713623846352979940529142984724747568191373312
2^150 = 1427247692705959881058285969449495136382746624
2^151 = 2854495385411919762116571938898990272765493248
2^152 = 5708990770823839524233143877797980545530986496
2^153 = 11417981541647679048466287755595961091061972992
2^154 = 22835963083295358096932575511191922182123945984
2^155 = 45671926166590716193865151022383844364247891968
2^156 = 91343852333181432387730302044767688728495783936
2^157 = 182687704666362864775460604089535377456991567872
2^158 = 365375409332725729550921208179070754913983135744
2^159 = 730750818665451459101842416358141509827966271488
2^160 = 1461501637330902918203684832716283019655932542976
2^161 = 2923003274661805836407369665432566039311865085952
2^162 = 5846006549323611672814739330865132078623730171904
2^163 = 11692013098647223345629478661730264157247460343808
2^164 = 23384026197294446691258957323460528314494920687616
2^165 = 46768052394588893382517914646921056628989841375232
2^166 = 93536104789177786765035829293842113257979682750464
2^167 = 187072209578355573530071658587684226515959365500928
2^168 = 374144419156711147060143317175368453031918731001856
2^169 = 748288838313422294120286634350736906063837462003712
2^170 = 1496577676626844588240573268701473812127674924007424
2^171 = 2993155353253689176481146537402947624255349848014848
2^172 = 5986310706507378352962293074805895248510699696029696
2^173 = 11972621413014756705924586149611790497021399392059392
2^174 = 23945242826029513411849172299223580994042798784118784
2^175 = 47890485652059026823698344598447161988085597568237568
2^176 = 95780971304118053647396689196894323976171195136475136
2^177 = 191561942608236107294793378393788647952342390272950272
2^178 = 383123885216472214589586756787577295904684780545900544
2^179 = 766247770432944429179173513575154591809369561091801088
2^180 = 1532495540865888858358347027150309183618739122183602176
2^181 = 3064991081731777716716694054300618367237478244367204352
2^182 = 6129982163463555433433388108601236734474956488734408704
2^183 = 12259964326927110866866776217202473468949912977468817408
2^184 = 24519928653854221733733552434404946937899825954937634816
2^185 = 49039857307708443467467104868809893875799651909875269632
2^186 = 98079714615416886934934209737619787751599303819750539264
2^187 = 196159429230833773869868419475239575503198607639501078528
2^188 = 392318858461667547739736838950479151006397215279002157056
2^189 = 784637716923335095479473677900958302012794430558004314112
2^190 = 1569275433846670190958947355801916604025588861116008628224
2^191 = 3138550867693340381917894711603833208051177722232017256448
2^192 = 6277101735386680763835789423207666416102355444464034512896
2^193 = 12554203470773361527671578846415332832204710888928069025792
2^194 = 25108406941546723055343157692830665664409421777856138051584
2^195 = 50216813883093446110686315385661331328818843555712276103168
2^196 = 100433627766186892221372630771322662657637687111424552206336
2^197 = 200867255532373784442745261542645325315275374222849104412672
2^198 = 401734511064747568885490523085290650630550748445698208825344
2^199 = 803469022129495137770981046170581301261101496891396417650688
2^200 = 1606938044258990275541962092341162602522202993782792835301376
...
--- powers of 3 ---
3^1 = 3
3^2 = 9
3^3 = 27
3^4 = 81
3^5 = 243
3^6 = 729
3^7 = 2187
3^8 = 6561
3^9 = 19683
3^10 = 59049
3^11 = 177147
3^12 = 531441
3^13 = 1594323
3^14 = 4782969
3^15 = 14348907
3^16 = 43046721
3^17 = 129140163
3^18 = 387420489
3^19 = 1162261467
3^20 = 3486784401
3^21 = 10460353203
3^22 = 31381059609
3^23 = 94143178827
3^24 = 282429536481
3^25 = 847288609443
3^26 = 2541865828329
3^27 = 7625597484987
3^28 = 22876792454961
3^29 = 68630377364883
3^30 = 205891132094649
3^31 = 617673396283947
3^32 = 1853020188851841
3^33 = 5559060566555523
3^34 = 16677181699666569
3^35 = 50031545098999707
3^36 = 150094635296999121
3^37 = 450283905890997363
3^38 = 1350851717672992089
3^39 = 4052555153018976267
3^40 = 12157665459056928801
3^41 = 36472996377170786403
3^42 = 109418989131512359209
3^43 = 328256967394537077627
3^44 = 984770902183611232881
3^45 = 2954312706550833698643
3^46 = 8862938119652501095929
3^47 = 26588814358957503287787
3^48 = 79766443076872509863361
3^49 = 239299329230617529590083
3^50 = 717897987691852588770249
3^51 = 2153693963075557766310747
3^52 = 6461081889226673298932241
3^53 = 19383245667680019896796723
3^54 = 58149737003040059690390169
3^55 = 174449211009120179071170507
3^56 = 523347633027360537213511521
3^57 = 1570042899082081611640534563
3^58 = 4710128697246244834921603689
3^59 = 14130386091738734504764811067
3^60 = 42391158275216203514294433201
3^61 = 127173474825648610542883299603
3^62 = 381520424476945831628649898809
3^63 = 1144561273430837494885949696427
3^64 = 3433683820292512484657849089281
3^65 = 10301051460877537453973547267843
3^66 = 30903154382632612361920641803529
3^67 = 92709463147897837085761925410587
3^68 = 278128389443693511257285776231761
3^69 = 834385168331080533771857328695283
3^70 = 2503155504993241601315571986085849
3^71 = 7509466514979724803946715958257547
3^72 = 22528399544939174411840147874772641
3^73 = 67585198634817523235520443624317923
3^74 = 202755595904452569706561330872953769
3^75 = 608266787713357709119683992618861307
3^76 = 1824800363140073127359051977856583921
3^77 = 5474401089420219382077155933569751763
3^78 = 16423203268260658146231467800709255289
3^79 = 49269609804781974438694403402127765867
3^80 = 147808829414345923316083210206383297601
3^81 = 443426488243037769948249630619149892803
3^82 = 1330279464729113309844748891857449678409
3^83 = 3990838394187339929534246675572349035227
3^84 = 11972515182562019788602740026717047105681
3^85 = 35917545547686059365808220080151141317043
3^86 = 107752636643058178097424660240453423951129
3^87 = 323257909929174534292273980721360271853387
3^88 = 969773729787523602876821942164080815560161
3^89 = 2909321189362570808630465826492242446680483
3^90 = 8727963568087712425891397479476727340041449
3^91 = 26183890704263137277674192438430182020124347
3^92 = 78551672112789411833022577315290546060373041
3^93 = 235655016338368235499067731945871638181119123
3^94 = 706965049015104706497203195837614914543357369
3^95 = 2120895147045314119491609587512844743630072107
3^96 = 6362685441135942358474828762538534230890216321
3^97 = 19088056323407827075424486287615602692670648963
3^98 = 57264168970223481226273458862846808078011946889
3^99 = 171792506910670443678820376588540424234035840667
3^100 = 515377520732011331036461129765621272702107522001
3^101 = 1546132562196033993109383389296863818106322566003
3^102 = 4638397686588101979328150167890591454318967698009
3^103 = 13915193059764305937984450503671774362956903094027
3^104 = 41745579179292917813953351511015323088870709282081
3^105 = 125236737537878753441860054533045969266612127846243
3^106 = 375710212613636260325580163599137907799836383538729
3^107 = 1127130637840908780976740490797413723399509150616187
3^108 = 3381391913522726342930221472392241170198527451848561
3^109 = 10144175740568179028790664417176723510595582355545683
3^110 = 30432527221704537086371993251530170531786747066637049
3^111 = 91297581665113611259115979754590511595360241199911147
3^112 = 273892744995340833777347939263771534786080723599733441
3^113 = 821678234986022501332043817791314604358242170799200323
3^114 = 2465034704958067503996131453373943813074726512397600969
3^115 = 7395104114874202511988394360121831439224179537192802907
3^116 = 22185312344622607535965183080365494317672538611578408721
3^117 = 66555937033867822607895549241096482953017615834735226163
3^118 = 199667811101603467823686647723289448859052847504205678489
3^119 = 599003433304810403471059943169868346577158542512617035467
3^120 = 1797010299914431210413179829509605039731475627537851106401
3^121 = 5391030899743293631239539488528815119194426882613553319203
3^122 = 16173092699229880893718618465586445357583280647840659957609
3^123 = 48519278097689642681155855396759336072749841943521979872827
3^124 = 145557834293068928043467566190278008218249525830565939618481
3^125 = 436673502879206784130402698570834024654748577491697818855443
3^126 = 1310020508637620352391208095712502073964245732475093456566329
3^127 = 3930061525912861057173624287137506221892737197425280369698987
3^128 = 11790184577738583171520872861412518665678211592275841109096961
3^129 = 35370553733215749514562618584237555997034634776827523327290883
3^130 = 106111661199647248543687855752712667991103904330482569981872649
3^131 = 318334983598941745631063567258138003973311712991447709945617947
3^132 = 955004950796825236893190701774414011919935138974343129836853841
3^133 = 2865014852390475710679572105323242035759805416923029389510561523
3^134 = 8595044557171427132038716315969726107279416250769088168531684569
3^135 = 25785133671514281396116148947909178321838248752307264505595053707
3^136 = 77355401014542844188348446843727534965514746256921793516785161121
3^137 = 232066203043628532565045340531182604896544238770765380550355483363
3^138 = 696198609130885597695136021593547814689632716312296141651066450089
3^139 = 2088595827392656793085408064780643444068898148936888424953199350267
3^140 = 6265787482177970379256224194341930332206694446810665274859598050801
3^141 = 18797362446533911137768672583025790996620083340431995824578794152403
3^142 = 56392087339601733413306017749077372989860250021295987473736382457209
3^143 = 169176262018805200239918053247232118969580750063887962421209147371627
3^144 = 507528786056415600719754159741696356908742250191663887263627442114881
3^145 = 1522586358169246802159262479225089070726226750574991661790882326344643
3^146 = 4567759074507740406477787437675267212178680251724974985372646979033929
3^147 = 13703277223523221219433362313025801636536040755174924956117940937101787
3^148 = 41109831670569663658300086939077404909608122265524774868353822811305361
3^149 = 123329495011708990974900260817232214728824366796574324605061468433916083
3^150 = 369988485035126972924700782451696644186473100389722973815184405301748249
3^151 = 1109965455105380918774102347355089932559419301169168921445553215905244747
3^152 = 3329896365316142756322307042065269797678257903507506764336659647715734241
3^153 = 9989689095948428268966921126195809393034773710522520293009978943147202723
3^154 = 29969067287845284806900763378587428179104321131567560879029936829441608169
3^155 = 89907201863535854420702290135762284537312963394702682637089810488324824507
3^156 = 269721605590607563262106870407286853611938890184108047911269431464974473521
3^157 = 809164816771822689786320611221860560835816670552324143733808294394923420563
3^158 = 2427494450315468069358961833665581682507450011656972431201424883184770261689
3^159 = 7282483350946404208076885500996745047522350034970917293604274649554310785067
3^160 = 21847450052839212624230656502990235142567050104912751880812823948662932355201
...


Who would have thought your humble Arduino could calculate 100 factorial! Or 2 to the power 300! It runs pretty fast too. 

Calculate e



// BigNumber test: calculate e
#include "BigNumber.h"

// function to display a big number and free it afterwards
void printBignum (BigNumber & n)
{
  char * s = n.toString ();
  Serial.println (s);
  free (s);
}  // end of printBignum

void setup ()
{
  Serial.begin (115200);
  Serial.println ();

  BigNumber::begin (50);  // max around 160 on the Uno

  // some big numbers
  BigNumber n = 1, e = 1, one = 1;

  int i = 1;
  BigNumber E;  // previous result

  unsigned long start = millis ();
  do
  { 
    E = e;
    n *= i++;  // n is i factorial
    e += one / n;
  }  while (e != E);
  unsigned long time = millis () - start;

  printBignum (e);
  Serial.print (time);
  Serial.println (" mS");
} // end of setup

void loop () { }


Output:


2.71828182845904523536028747135266249775724709369978
629 mS


Theory:

http://en.wikipedia.org/wiki/E_%28mathematical_constant%29

E can be calculated as:


1 + (1/1!) + (1/2!) + (1/3!) ...


That's why the code above is calculating running factorials, and adding the inverse of the factorial to the running total. The code breaks out of the loop when, for the desired number of decimal places, the calculated value doesn't change. That is, at this level of precision, the new amount added does not change the result.

BigNumber class


The C++ BigNumber class handles allocation and deallocation in the constructor and destructor.

For example, factorials can be produced like this:

Code:


  BigNumber::begin ();  // initialize library
 
  //factorials
  BigNumber fact = 1;

  for (int i = 2; i <= 200; i++)
  {
    Serial.print (i);
    Serial.print ("! = ");
    fact *= i;
    printBignum (fact);
  }


The normal arithmetic operations are supported (eg. assignment, add, subtract, divide, multiply, modulus). Also things like a++ or a--.

Also comparisons can be done in the natural way.

The only memory allocation you have to worry about is when you get a number to print. Since the library may have to return any size number, it does a malloc to store the number (plus a sign, and decimal point if required). It is up to you to free that string. eg.


// function to display a big number and free it afterwards
void printBignum (BigNumber n)
{
  char * s = n.toString ();
  Serial.println (s);
  free (s);
}  // end of printBignum


An important parameter is the "scale" of the number, which you can set with setScale (n). The scale is effectively the number of decimal places.

For example:


  BigNumber::begin ();  // initialize library

  BigNumber a, b = 2, c;
 
  BigNumber::setScale (0);
  a = BigNumber (1) / BigNumber (3);
  c = b.sqrt ();
  Serial.print ("1/3 = ");
  printBignum (a);
  Serial.print ("sqrt(2) = ");
  printBignum (c);


Output:


1/3 = 0
sqrt(2) = 1


Change the scale to setScale (20) and we get:


1/3 = 0.33333333333333333333
sqrt(2) = 1.41421356237309504880


Change the scale to setScale (100) and we get:


1/3 = 0.3333333333333333333333333333333333333333333333333333333333333333333333333333333333333333333333333333
sqrt(2) = 1.4142135623730950488016887242096980785696718753769480731766797379907324784621070388503875343276415727



So clearly the scale is affecting the results. Note that, of course, the larger the scale the slower the calculation and the more memory it will require.

Some caveats



  • Working with large numbers is necessarily slow - the larger the number, or the more decimal places, the slower.

  • Each digit requires a byte of memory, plus some overhead (eg. where the decimal point is) - large numbers will soon gobble up the available memory.

  • Doing a toString also requires memory - a byte per digit, plus the sign, decimal point, and trailing 0x00 byte.

  • An "error" condition inside the library (eg. running out of memory) calls exit(), effectively sending the library into a tight loop.

  • You may need to cast some numbers to avoid "ambiguous" warnings from the compiler.

  • If you only have 2048 bytes of RAM, you clearly need to use a library like this with caution. Running out of memory will be quite likely unless you closely manage the size of your numbers, and how many you have.

  • Memory fragmentation will quite possibly be a problem, particularly if you calculate numbers of different sizes (eg. factorials).


The supplied library has some example code (eg. powers, factorials, sine calculations, e^x, and ln(x) ).

Note that cosine and tangent can effectively be calculated from the sine.

- Nick Gammon

www.gammon.com.au, www.mushclient.com
[Go to top] top

Posted byNick Gammon   Australia  (21,293 posts)  [Biography] bio   Forum Administrator
DateReply #1 on Tue 22 Jan 2013 05:28 AM (UTC)

Amended on Tue 22 Jan 2013 06:16 AM (UTC) by Nick Gammon

Message
Improvements to printing


Thanks to suggestions from Paul Stoffregen, the library has now been modified to allow you to directly print big numbers.

For example, the Factorials example now looks like this:


// BigNumber test: factorials
#include "BigNumber.h"

void setup ()
{
  Serial.begin (115200);
  while (!Serial) ;
  delay(500);
  Serial.println ();
  BigNumber::begin ();  // initialize library
 
  //factorials
  BigNumber fact = 1;

  for (int i = 2; i <= 200; i++)
  {
    Serial.print(i);
    Serial.print("! = ");
    fact *= i;
    Serial.println (fact);
  }

}  // end of setup

void loop () { }


Modified line in bold. This was done by deriving the BigNumber class from the Printable class. This means that you can now print big numbers from any class derived from Stream (eg. Serial, Serial1, etc.).

Also changed slightly to support chips which did not have an exit() function defined in their library.

- Nick Gammon

www.gammon.com.au, www.mushclient.com






728x90
728x90

정수만 갖고 코딩하는것도 초보 수준인데 개념만 살짝 갖고 있는 float 변수형의 16자리수 계산에 대해 개념을 잡으려니 안개처럼 몽실몽실하게 흩어지는군요.





출처: http://elenoa.tistory.com/241

일단 부동소수점이 정확하기 힘들다는 것은 알았습니다.

이진수로 십진수를 계산하기 때문에 어쩔 수 없는 문제지요. 

예전에 인텔도 CPU에서 부동소수점 처리에 결함이 생긴 펜티업 칩 때문에 큰 손실을 본 적이 있습니다(링크)

그리고 저는 고작 10여자리의 부동소수점 때문에 골머리를 썩고 있네요.





아두이노의 레퍼런스를 읽어봅니다





6-7자리의 정확도를 갖고 있다는군요. 

거기다 저는 연산을 해야 하기 때문에 곱셈/덧셈을 할때마다 정확한 자리수가 줄어들겠죠?

생각해보니 이것도 큰 문제네요. 소숫점 이하 50자리까지 정확하다고 해도 그 숫자끼리 몇번 곱하면 곱할때마다 자릿수의 절반씩은 믿을 수 없게 될텐데요





double 을 사용한다고 해도 모자랍니다. 




비슷한 문제를 저만 겪는 건 아닐 것 같아 검색을 해보니 포럼에 비슷한 토론이 많이 있는데 딱히 이거다 하는 해결책은 안보이는군요.





하드웨어의 한계도 있어서 이런 물건도 나오는 듯 합니다. 




그 와중에 GitHub에서 SoftFloat 이라는 아두이노 라이브러리를 찾았는데

description이 하나도 없어서 이해를 못하겠네요;; 헤더파일 보고 해석할 역량은 안되는데 말이죠

https://github.com/mmoller2k/Float64



728x90
728x90


키보드 매트릭스를 테스트하는 중인데 이상하게 2열의 1,2,3 등의 숫자만 입력이 안되더군요






핀에 문제가 있나 하고 핀아웃도 다시 확인하고






배선설정과 실제 스케치간에 연결이 다른부분이 있나 다시 확인해봤습니다. 

문제는 그냥 제가 시리얼로 결과를 확인하고 있다는 것이었지요

Tx 핀으로 입력을 하는데 그걸 시리얼 출력으로 쓰고있으니 당연히 안되는 것이었습니다. 




수정해서 키패드 입력을 LED 디스플레이로 하는건 금방 되었는데

본격적으로 계획을 짜보니 이게 생각보다 난이도가 상당히 높네요.

스케치를 짜려고 보니 생각해야 할 부분이 많습니다.


1. 키패드 매트릭스는 사칙연산 부호 등 때문에 char 형태로 데이터를 주고받음 -> '0' 문자를 숫자로 변경하는건 쉬움. 

2. 25개의 매트릭스 입력에 따라 숫자, 문자 등으로 분류하여 각각 다른 계산을 해야함 -> 역시 어렵진 않을듯. 

3. 계산기의 자리수는 16자리이므로 최대 9999999999999999 까지 표시할 수 있다. 

소수점을 사용해야 하므로 float 변수를 사용하는데 소수점 이하를 표시하려면

앞에 표시될 '0.' 글자를 빼면 소수점 14자리까지 쓸 수 있어야 한다. 

기본적으로 디스플레이에서 float 함수를 쓰면 소수점 2번째 자리까지만 표시되며

"%f" 형을 사용해 float 형을 출력하면 이하 숫자의 오류가 생긴다. 

dtostrf() 함수를 사용하면 3번째이하 자리수를 처리할 수 있지만 

소수점 이하 자리수를 정확히 알고 있는 경우가 아니면 역시 오류가 생긴다 ->갑자기 최종보스 출현한 난이도..;


검색해보니 부동소수점 문제는 원래 어렵더군요.. 

아두이노 계산기 예제라고 나와있는것도 죄다 정수처리만 가능한 간단형 버전이고요.



913425.45 를 출력하면 저렇게 나옵니다.

일단 정확하게 출력하는것도 문제지만 그걸 또 연산처리해야한다는 점이 엄청 골치아프네요

728x90
728x90

아예 AVR 정품 AVR ISP 를 사고싶은 마음도 있지만 

이건 그냥 장비병인 것 같습니다.  쇼핑몰만 둘러보다 포기.




Aliexpress에서 호환 AVRISP MKii 를 샀는데 도착하고 보니 Vcc 에 전원이 안 들어오는 불량품이네요..

일단 Dispute 넣고 그냥 아두이노에 ArduinoISP 넣고 Atmega128에 부트로더를 구웠습니다. 



사실 지난번 ISP 드라이버 안 잡혔을때 이렇게 할까 했지만 미루다 보니 이렇게 됐네요

그냥 아두이노 보드 하나 잡아서 ISP를 따로 만들어 두어야 하나 생각중입니다. 






마찬가지로 지난번에 케이스에 넣었던 FTDI 보드로 업로드했더니 잘 됩니다. 

Blink로 빨간색 LED를 껐다 켰다 해 보았습니다. 






처음에 Atmega128을 쓰려고 했던 이유가 아두이노 핀이 모자랄 것 같아서였습니다

마침 Atmega128 칩도 많이 있는 이유도 있었죠.

그런데 아두이노 보드를 하나하나 체크해 보니 핀이 모자르진 않다는 걸 알게 되었습니다. 

오히려 딱 맞게 쓰고 한두개는 여유있을 정도네요


덕분에 좀 쉽게 갈 수 있을 것 같습니다. 





항상 CNC로 보드를 깎아 버리는걸 선호하지만

이번에는 추가로 주변회로가 어떻게 변할 지 몰라서 

전용 테스트 보드를 만들기에는 문제가 있습니다. 

일반 단면 만능기판에 테스트 보드를 구성하기로 했습니다. 




LED 디스플레이 선을 연결하고 테스트해봤습니다. 

이번 작업은 여기까지입니다.




728x90
728x90


변환보드를 하나 살까 했는데 변환보드 하나에 6000원이라 


에라 하고 이글캐드를 실행해서 보드를 만들고 CNC로 깎았습니다. 


역시나 패턴이 좁아서 실패를 두어번 했네요










USBASP로 부트로더를 심으려고 하는데 안됩니다. 


에러 메세지를 보니 USBASP가 안 잡힌답니다.  


분명 드라이버를 설치했는데 말이죠.


부트로더를 쓸 때마다 최신 운영체제에 대응이 늦어 골때리는 경우가 자주 생기는군요


단순히 시키는 대로 해볼 뿐이라 이런 경우 어떻게 대응해야 하는지 잘 모르고 그대로 스톱됩니다. 






원래 계획대로 쉬프트 레지스터를 쓸지 말지 생각중입니다. 

728x90
728x90

기계식 키보드의 키를 심어서 계산기를 만들면

타격감과 오타율이 적은 계산기를 만들 수 있지 않을까 하던 중에

단순히 기존 계산기를 모딩하지 않고 아예 아두이노로 제작할까 하는 생각이 들었습니다. 






그리고 디스플레이를 전에 구해놓은 HCMS-2912 디스플레이를 이용해서 만들면 

참 이쁜 물건이 될 것 같더군요.







계산기의 키패드는 보통 5열 5행이기 때문에

5*5 키패드 매트릭스가 필요합니다. 








5*5 매트릭스는 10개의 입력핀이 필요하기 때문에

아두이노에서 직접 입력을 받는건 힘들고

74HC165 같은 쉬프트 레지스터를 이용하게 됩니다. 









그래서 74HC165 를 일단 몇개 구매했습니다. 

그리고 아두이노 보드를 계산기 기판에 그대로 심으면 높이 차이가 많이 생겨 케이스를 씌우는 데 무리가 따를 것 같아

아예 계산기 보드에 아두이노를 포함시키려 했습니다. 







그런데 부품박스를 열어보니 ATMEGA168 옆에 ATMEGA128 칩이 보입니다. 






검색해보니(링크) 아두이노로 사용 가능합니다. 







핀 수가 훨씬 많기 때문에 쉬프트 레지스터 없이 바로 사용이 가능하겠네요


결국 ATMEGA168(아두이노)+쉬프트 레지스터 로 가느냐

아니면 ATMEGA128 을 아두이노로 만들어서 쓰느냐 하는 문제인데

ATMEGA128이 쓸데없이 재고가 많은 관계로 이걸 쓰기로 했습니다. 






728x90
728x90



회로는 이제 거의 손댈 부분이 없습니다. 


나중에 케이스 만들때 완성형 보드는 새로 만들어야 겠지만 스키메틱은 바뀌지 않을 듯 합니다.


중간에 DC 모터펌프를 사용한 버전을 만들어 보았다가 


취소하고 다시 스텝모터로 돌아오는 바람에 시간이 많이 걸렸네요



수정사항은 몇개 없지만 전원을 넣을 때마다 일정 확률로(?) 스텝 드라이버가 터지는 바람에


한 4개쯤 날려먹고.. 컨덴서를 몇개 추가하고 전원 스위치를 더했습니다. 








정량펌프는 전에 못보던 깔끔한 물건이 나왔길래 구매해봤는데


꽤 괜찮습니다. 크기도 적당하고 그냥 이걸로 가야겠네요








드라이빙 전류는 0.2A 정도가 적당하더군요










이제 최종적으로 코드를 마무리해야 합니다.


그러려면 펌프가 회전하는 수에 비해 펌프질되는 유량이 얼마나 되는지 측정해야 하므로


간단한 코드로 800ml 정도 물을 펌프질해봤습니다. 


OLED에 나오는 숫자는 모터의 회전 수입니다. 


3079회전 = 물 605g

4000회전 = 물 778g

(물 1g = 1ml)

7079회전 - 1383ml 이므로

1ml 당 5.12회전
1회전당 0.195ml


모터 70회전에 물방울은 355방울이 떨어졌고


마이크로스텝 1/16 이므로


3200스텝 = 1회전= 5.07방울 = 0.195ml 입니다


-> 고속과 저속에서 유량이 달라지더군요; 주로 쓰는 속도 기준으로 재측정할 예정입니다. 



스텝 딜레이는 40us 정도가 최하이며 그 이하로 내리면 가감속 코드 없이는 탈조가 납니다. 



코드를 최종적으로 수정한 다음 케이스를 씌워야 하는데


이럴땐 같이 작업하는 디자이너 한명 있으면 좋겠다 싶네요. 


매번 어떻게든 더 이쁜모양 만들어 보려고 발버둥 칩니다.

728x90
728x90




인코더 스위치를 넣어서 회로를 짜놓고


코딩을 하려니 어렵더군요.. 


일단 간단한 입력은 되는데 


인코더의 입력을 놓치지 않고 받아들이기 위해선 인터럽트가 필요하고


이제 간신히 u8glib 조금씩 이해가 가는 와중에 


인터럽트 집어넣으려니 머리가 뱅글뱅글 도네요.




스킬업한 다음에나 생각해볼 일인 것 같아 제거하고


토글 스위치 3개(up,down,select) 넣고 약간 생각해 보니


이것도 디바운스나 동시입력에 대한 부분을 처리해야 해서 뭔가 골치아파지는것을 느꼈습니다.









인스트럭터블스에서 본 기억을 찾아내서 다시 자료를 검색해보고


단순히 아날로그 입력 1핀만으로 여러개의 스위치 사용이 가능한 방법을 썼습니다. 


위와 같이 직렬 저항 사이에 스위치 입력을 넣으면 


5V 입력이 분배가 되어 스위치를 누를때마다 0-1023 에서 특정한 범위의 값으로 들어오게 되고


그걸 확인해서 스위치 입력을 확인하는 방법입니다. 




써보니 많은 장점이 있더군요.


1.여러개의 스위치를 1핀으로 간편하게 확인 가능하다.

2.디바운스 처리가 쉽다

3.여러개의 스위치를 동시입력하는 경우도 처리 가능하다

4.입력값 처리에 따라 스위치를 둔감하게 혹은 민감하게 조정 가능하다







처음 만들었던 회로 뒷면에 다시 납땜해서 수정했습니다. 







원하는 값을 스위치로 변경해서 입력하고 메뉴를 전환하면 단계별로 메뉴가 바뀌는 부분까지 마쳤습니다. 


화면 바뀔때마다 구성이 다른데 기본동작이 완료되면 수정할 계획이고요


이제 입력된 값을 바탕으로 스텝모터를 돌리는 부분을 진행할 차례군요







728x90
728x90

화면에서 일단 간단한 로고나 메세지를 보여준 후


메뉴로 넘어가고 그 다음 메뉴로 넘어가는 등의 구성을 생각했습니다.


그래서 일단 텍스트로 꾸며봤는데



void loop() {


  u8g.firstPage();  //OLED 루프

  do {

    switch(draw_state){

      case 0:StartPage();delay(500)break;

      case 1:SecondPage();delay(500);break;    

    }

    }

  while( u8g.nextPage() ); 


이렇게 u8glib 함수 사이에 딜레이를 넣어봤습니다. 








첫번째 화면을 뿌리고 잠시 후에 두번째 화면으로 바뀌어야 하는데


두 화면을 동시에 뿌리려는 듯 겹친 화면이 나옵니다. 




void StartPage(){

   u8g.drawStr(0,10,"ColdBrewSystem 0.9");

   u8g.drawStr(0,25,"pashiran's");

   u8g.drawStr(0,40,"workspace");

   delay(500);


그래서 위와 같이 호출하는 화면함수에 딜레이를 넣었습니다. 





그랬더니 화면 자체에 딜레이가 걸려버립니다. 



여기저기 딜레이 위치를 바꿔봤지만 해결이 안되었는데







void loop() {


  u8g.firstPage();  //OLED 루프

  do {

    switch(draw_state){

      case 0:StartPage();break;

      case 1:SecondPage();break;    

    }

    }

  while( u8g.nextPage() );



if(draw_state==0){

  draw_state++;

}

else{

  draw_state=0;

}

delay(500);


} //loop의 끝 


이렇게 해야 하니 정상적으로 나옵니다. 


기본적으로는 u8glib이 함수 호출하면 메모리에 디스플레이 할 정보를 불러들이고서 


메모리를 읽어서 화면에 뿌려주는 방식이라  


그 과정 사이에 명령어를 사용할 때는 주의해야 하더군요.






728x90
728x90


저희 집 식구들은 커피를 많이 마시는 편인데


빨대로 간이 더치커피 기계를 만들어 사용해왔습니다만


물조절도 불편하고 공간도 차지하고 여러모로 불편한 부분이 있습니다. 



전에 정량펌프를 알리 익스프레스에서 구매하여 사용해봤지만 


DC 모터를 이용한 싸구려 펌프라서 토츌량도 적당하지 않고 금방 고장나버리더군요.



최근에 더워서 커피 소비량이 늘다보니 다시 한번 마무리해봤는데


저기다가 아두이노+스텝드라이버+파워+LCD를 추가할 생각하니


덩치가 좀 큰듯 하네요.  




시제품 만들어보고 수정할지 말지 생각해봐야겠습니다. 



728x90
728x90

일단 테스트용으로 만든 정량펌프를 돌려봤습니다. 




설계 자체는 큰 문제가 없는 듯, 미묘하게 치수를 조정해야 할 부분은 있지만 일단은 돌아갑니다. 








최저속으로 돌렸을 때 모습입니다. 물방울이 덜덜 떨리는군요.. 



추가할 부분:

1.호스를 고정할 고정부 설계


2.스텝모터에 맞는 볼트 구매


3.마이크로스텝 설정 가능하도록 할 것. 


4. DC 기어드모터를 써도 괜찮을 것 같음. 테스트해볼것. 


728x90
728x90




이렇게 생긴 펌프를 정량펌프 - Peristaltic Pump 라고 합니다. 


신축성이 있는 호스를 원형의 바퀴로 눌러서 밀어내는 방식의 펌프죠.


저속으로 매우 천천히 소량씩 주입해야 하는 약품용 펌프나 의료기기 기타 전문 산업용으로 쓰입니다.


스텝모터를 조합해서 저속의 정량펌프를 만들면 여기저기 쓸데가 있겠다 싶어 


한개 만들어 보려고 얼마전부터 그려보는 중입니다. 







판재로 입체물을 그리는건 참 번거롭습니다. 


cam을 빨리 마스터하던가 3D 프린터를 마련하던가 해야 좀 편할텐데요..








정량펌프의 단점 중 하나는 실리콘 호스가 압축된 상태로 이송된 뒤 출구가 풀어지는 구조상


맥동이 있다는 것입니다. 일단 맥동을 좀 덜 생기게 할 요량으로 입출구를 최대한 스무스하게 그려보긴 했습니다만..


만들어 보면 보나마나 맥동이 생길 것 같긴 합니다. 









베어링 위치가 호스 위치랑 맞아야 하는데 가진 재료에 맞게 하려니 


3,5T판재 조합의 두께에 따라 설계를 변경해야 하는 문제도 있습니다. 


베어링도 생각보다 작은걸 왕창 사두는 바람에.. 제대로 돌아갈까 좀 의문이긴 합니다.



만들어 보면서 수정해야 할 것 같네요.


728x90
728x90



전에 생활용품으로 더치커피 메이커 만들기(링크)


를 만들어서 더치커피를 이후로 쭉 먹고 있는데



맛있습니다! 맛있고 먹기 편해요!




그런데 이마저도 만들기 귀찮음;;


원두 갈고 세팅하고 물 양 맞춰서 사이펀 돌리고 


뭐 이런 과정들을 좀 더 편하게 할 수 없을까 하다가



알리익스프레스에서 구입한 작은 펌프모터와


CNC로 PCB 만들기(링크) 에서 만들었던 PWM 속도 제어기로 물을 천천히 한방울씩 떨어트릴 수 있을 것 같아


두개를 조합해 봅니다. 








정역회전 스위치를 달아줬고요. 12V 어댑터로 구동합니다. 













기본 호스는 너무 짧아서 옥션에서 구입한 실리콘 호스로 교체.





거의 최저속도로 돌려야 비교적 물이 천천히 떨어지다 보니 힘이 없어서 물방울이 정확한 간격으로 떨어지지는 않네요.



호스 클립이나 컵 받침 등 몇가지 파트를 더 붙여서 완성할 계획입니다. 





-------------------------------------------7/15 추가--------------------------------------------------------


오늘 펀샵에 이런게 올라왔네요


22000원짜리 더치세트;;


http://www.funshop.co.kr/goods/detail/28935?t=hv2#



어흑



원래 저거 하나 더 만들어서 CNC 알콜 공급용으로 쓰려고 했는데 


그냥 저걸 그쪽으로 돌리고 펀샵 더치세트를 하나 사야겠습니다. 




728x90
728x90

더치커피를 '갑자기' 먹고 싶어서 알아보니 은근 비싸더군요.

 

링거용 수액 세트로도 쉽게 만들 수 있습니다만..

 

집근처 약국 및 지나가다 보이는 약국 6곳을 돌아봐도 모두 없음.

 

 

집에 있는 물건들로 해결했습니다.

 

핵심 부품은 비닐봉지용 집게, 볼트, 빨대, 스카치 테잎 정도만 있으면 됩니다.

 

 

 

 

거의 90% 다이소 잡화코너에서 구입 가능한 물건들로 제작 가능하더군요.

 

 

비닐봉지 집게입니다. 다이소에서 1000원에 5개인가 들어 있을겁니다.

 

 

 

 

 

 

 

 

 

 

 

 

 

적당히 안쓰는 볼트 하나만 있으면 됩니다. 집게에 구멍을 2개 뚫습니다.

 

한개는 볼트 지름보다 약간 작게, 한개는 볼트 지름보다 크게.

 

 

 

 

 

 

 

그리고 볼트를 끼웁니다. 그러면 작은 구멍쪽에만 볼트가 고정되면서,

 

볼트를 조일때 집게가 조여지겠죠.

 

이게 없어도 빨래집게나, 나무젓가락 등으로도 해결 가능하겠더군요.

 

 

 

 

 

 

 

 

 

 

 

그리고 빨대와 볼펜을 준비합니다. 볼펜은 미리 깨끗이 씻어줍니다.

 

빨대는 주름관이 있어 접히는 것으로 준비하세요.

 

어차피 원두 사오셔야 하면 카페에서 얻어도 되고요.

 

주름이 없어도 라이타불로 약간씩 휘어가며 만들 순 있습니다만, 있는게 편합니다.

 

 

 

 

 

 

 

 

볼펜을 눌러 끼운 채로, 라이터로 돌려가며 살짝 가열해줍니다.

 

 

 

 

 

 

 

 

이 과정을 두어번 해주면 빨대가 요렇게 살짝 벌어집니다.

 

 

 

 

 

 

 

 

 

 

그러면 쉽게 끼울 수 있습니다.

 

 

이 과정을 몇번 반복해서 빨대를 4~5개 정도 연결합니다.

 

빨대 갯수는 자기 집 찬장과 싱크대 높이차를 커버할 정도?+1개 로 맞추면 됩니다.

 

 

 

 

 

 

 

 

 

 

 

 

 

테스트해보니 한곳에서 물이 새길레 수도관용 테프론 테이프로 말아줬습니다.

 

그냥 새로 만들어도 됩니다. 빨대니까요.

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

커피 원두는 동네 카페에서 더치용으로 갈아달라고 하거나 적당히 구하시면 됩니다.

 

일단 있는 원두를 대충 갈았습니다.

 

저는 드립커피용 드리퍼를 사용했는데,

 

500ml 페트병 같은걸로도 가능하고 뭐가 됐던 거름망으로 적당히 걸러주면 되겠죠.

 

사진이 없는데 저 위에 거름망을 동그랗게 잘라 덮으세요.

 

그냥 한가운데로만 물이 떨어지면 가장자리쪽은 물이 안 지나가니 효과가 없게 됩니다.

 

 

 

 

 

 

 

 

 

 

 

 

어째 대충 만들다 보니 전체 사진이 없네요. -_-;;

 

다 만든 후 빨대를 이용해서 위와 같이 사이펀 구조를 만들면 됩니다.

 

그리고 B 쪽의 빨대 하단부에 아까 만든 집게를 끼우고 드라이버로 조절해 가며 물이 떨어지는 정도를 조절합니다.

 

 

 

 

 

 

 

 

 

 

집에 있던 물통에 빨대를 꽂습니다.

 

그리고 바깥쪽에는 스카치 테잎으로 고정해서 빨대가 빠지지 않도록 한 후,

 

출구쪽에서 입으로 살짝 빨면 물이 빨려나오고 중력으로 인해 물이 계속 나오게 되죠.

(이 초기작업은 싱크대에서 하세요. 아차하면 물바다 됩니다)

 

남들과 같이 드실거면 입으로 빤 빨대 끝은 가위로 잘라주시고요.

 

 

 

그리고 집게를 조정해서 적당히 물이 떨어지도록 합니다 .

 

 

 

 

 

 

최종적으로 물이 떨어지는 양은

 

현재 수면에서 빨대 끝이 위치한 부분 까지의 차이에 좌우됩니다.

 

밤새 뒀다가 흘러넘칠 수도 있으니 미리 맞춰놓으시고요.

 

 

 

 

 

 

 

 

 

물이 저렇게 곱게 한방울씩 잘 떨어집니다.

 

 

 

 

 

 

 

 

내일 아침을 기다리며..

 

 

 

 

 

2014/3/6 추가: 생각보다 맛있어서 ^^ 잘 먹게 되는군요.

커피를 좋아하시지만 집에선 맛있는 커피를 먹기 힘들어 불편해 하시던 어머니께 갖다드렸더니

맛있고 편하다고 좋아하시네요. -커피셔틀 확정.

 

2014/3/9 추가: 검색해보니 pet 병 같은 것에 밑에 얇게 바늘뚫는 구멍을 뚫어서 사용하는 방법도 있는데

이 경우는 장점으로 단순하고 공간을 덜 차지하는 점이 있지만

물이 줄어들수록 압력이 줄어들어 초반과 후반에 물이 나오는 속도가 다르다는 단점이 있네요.

 

사이펀 방식은 빨대 내부의 물의 무게차로 빨려 나오는 것이기 때문에 빨대를 약간 길게 하면

물이 다 떨어질 때까지 떨어지는 속도가 일정하다는 장점이 있습니다.

단점으로는 높이차를 둬야 해서 물통을 올려놓고 빨대 설치하고 조정하는 약간 귀찮은 부분이 있고요.

728x90

+ Recent posts