2015년 12월 30일 수요일

gdb print stl

gdb쓸 때 vector, map등 stl이 pretty하게 보이지 않으면 다음을 이용한다.

https://sourceware.org/gdb/wiki/STLSupport

링크에 세가지 방법이 있는데, 첫번째 방법만 써도 거의 모든 문제가 해결된다.
혹시 링크 깨질까봐 옮겨두자면,
svn co svn://gcc.gnu.org/svn/gcc/trunk/libstdc++-v3/python
하고, ~/.gdbinit에 다음을 추가.
sys.path.insert의 path에는 위에서 받은 python directory의 path를 넣어준다.
python
import sys
sys.path.insert(0, '/home/maude/gdb_printers/python')
from libstdcxx.v6.printers import register_libstdcxx_printers
register_libstdcxx_printers (None)
end

2015년 9월 11일 금요일

merge arrays




그냥 간단하게 하면 되는 것을 꼼수를 써보겠다고 쇼를 했다.
자세한건 다음에...


#include <iostream>#include <vector>#include <algorithm>
#define v std::vector<int>
v MergeArrays(v A, v B) {  v u(100),n(100),x(100);  n.resize(set_intersection(A.begin(), A.end(), B.begin(), B.end(), n.begin())-n.begin());  x.resize(set_symmetric_difference(A.begin(), A.end(), B.begin(), B.end(), x.begin())-x.begin());  u.resize(set_symmetric_difference(n.begin(), n.end(), x.begin(), x.end(), u.begin())-u.begin());  u.resize(unique(u.begin(), u.end())-u.begin());  return u;}
int main() {  v r = MergeArrays({10,10,10,15,20,20,25,25,30,7000},{10,15,20,20,27,7200});  for(int i:r)    std::cout << i << ", ";
  return 0;}


2015년 8월 27일 목요일

bash prompt color

일과는 별로 상관 없는 것인데 은근히 꾸준히 찾아보게 된다.
stackoverflow에 정말 great한 answer가 있어서 링크
http://stackoverflow.com/a/20983251/766330

2015년 8월 25일 화요일

digital sum

https://codefights.com/challenge/hmnrz6mxXZWNRAkZu

35char가 말이 되나?
답이 나오면 꼭 봐야지.

int Digital_sum(int a) {
  return a%9 ?: 9;  
}

9거법.
내가 한심하다.

last digit

아 오늘 할것 있었는데 한문제에 또 낚여가지고.. ㅜㅜ

아래 식을 구하는 프로그램이다.
https://codefights.com/challenge/BNLZseQgvXBRPPBFr

$$ \sum _1 ^n n^n \mod 10 $$

일단 내 나름의 답은 아래와 같다.
int s,g,j,t,i,last(std::string N) {
  t = N.size();
  for(;++j<=atoi(N.substr(t>2?t-2:0).c_str());s+=g)
    for(g=1,i=j;i--;)
      g = g*j%10;
  return s%10;
}


나중에 1, 2등의 답안을 보니 atoi대신 stoi를 썼으면 몇자 더 줄일 수 있었다.
1등답안은 또 같은 사람인데, 이번엔 2등답안이 더 훌륭하다. 2등이 조금만 더 신경썼어도 여유롭게 1등할 수 있었을텐데 쓸모없는 변수조차 지우지 않는 여유를 부렸다.
1등답안은 좀 찬찬히 살펴봐야겠다 아직 이해가 안감.
int n, i, r, last(std::string N) {
  N="0"+N;
  for(r=N[n=N.size()-2]*7-6; i<4; )
r+="                                         "[N[n]%2*40+4*N[n+1]-192+i]%2<<i++;
  return r%10;


}
(with l in vim. all spaces are replaced to underscore.
int_n,_i,_r,_last(std::string_N)_{$
__N="0"+N;$
__for(r=N[n=N.size()-2]*7-6;_i<4;_)$
r+="____^I___^I_^I__^I_____^I^I^I__^I__^I_^I_____^I^I^I^I_____^I___^I^I^I______^I^I_^I___^I^I^I___^I____^I^I^I^I_"[N[n]%2*40+4*N[n+1]-192+i]%2<<i++;$
__return_r%10;$
}$
)
공백은 캐릭터 숫자로 포함되지 않아서 그것을 이용한 뭔가 굉장히 tricky한 방법 같은데 도무지 알수가 없다. abusing에 가깝지 않은가 싶기도 하고. 

성의없는 2등답안은 다음과 같은데,
int n, l, h, m, last(std::string N)
{
  n = N.size();
  l = std::stoi( N.substr( --n ? --n : 0));
  for(m = 0; l; l--)
    m += pow(l, l % 4 ? l % 4 : 4);
    
  return m % 10;
}
약간만 손보면 다음과 같이 된다.
int n, l, m, last(std::string N)
{
  n = N.size();
  l = stoi( N.substr( --n ? --n : 0));
  for(;l; l--)
    m += pow(l, l%4 ? : 4);

  return m%10;
}

문제를 처음 봤을 때 2등답안같은 답이 가능할것 같아서 좀 찾아봤는데 워낙 수학실력이 형편없다보니 저런 단순한 식에는 접근조차 못했다.
In[233]:= i = Range[100]; 

In[234]:= r1234 = PadRight[Range[4], Length@i, Range[4]]

Out[234]= {1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, \
4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, \
3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, \
2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4, \
1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4}

In[239]:= Mod[i^i , 10] == Mod[i^r1234, 10]

Out[239]= True

아름답다.


2015년 8월 24일 월요일

overlap point

이번에도 역시 codefight
https://codefights.com/challenge/7BLpypv6zjpr25iPY/solutions

1등은 이번에도 역시 같은 사람
코드는
#define f(x) hypot(i/9-4-x 0], i%9-4-x 1])<=x 2]
int i, r;
template <class T>
int overlapPoint(T a, T b) {
  for(;i++<99;)
      r+=f(a[) & f(b[);
  return r;
}

볼때마다 배울 것이 생기니까 아직까지는 지루하지 않다. 볼 시간이 많지 않은것이 흠이라면 흠.

핵심은 두가지다. 하나는 hypot함수, 하나는 평면의 격자를 루프 한번에 해결하는 것.
hypot함수 외에도 math.h에 희한한 함수들이 더 있는 것 같은데 처음 봤다. 짬날때 봐야 할 것 같다(하지만 보지 않겠지 -_-)

평면의 모든 격자는 예를 들어 다음과 같이 하면 쉽다
for(; x--; )
  for(; y--; )
    // do sth. (x,y) coord.

위에서는 변수를 하나만 만들고 정수 나눗셈과 modular를 이용해서 모든 격자점을 구해낸다. 참 놀라운 아이디어다.
99까지밖에 루프를 돌지 않는데 이건 테스트케이스가 작아서 운이 좋았던 것 같다. 그래도 예상할 수 있는 모든 범위에 대해 확장할 수 있으니 큰 문제는 없어보인다.

아래는 mathematica로 격자점을 구해본것. 격자점이 어떻게 모두 구해지는지 조금 더 직관적으로 볼 수 있다.
In[148]:= i = Range[0, 99]

Out[148]= {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, \
17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, \
34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, \
51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, \
68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, \
85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99}

In[157]:= i / 9 - 4 // Floor

Out[157]= {-4, -4, -4, -4, -4, -4, -4, -4, -4, -3, -3, -3, -3, -3, \
-3, -3, -3, -3, -2, -2, -2, -2, -2, -2, -2, -2, -2, -1, -1, -1, -1, \
-1, -1, -1, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, \
1, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 4, 4, \
4, 4, 4, 4, 4, 4, 5, 5, 5, 5, 5, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 6, 6, \
6, 7}

In[158]:= Mod[i, 9] - 4

Out[158]= {-4, -3, -2, -1, 0, 1, 2, 3, 4, -4, -3, -2, -1, 0, 1, 2, 3, \
4, -4, -3, -2, -1, 0, 1, 2, 3, 4, -4, -3, -2, -1, 0, 1, 2, 3, 4, -4, \
-3, -2, -1, 0, 1, 2, 3, 4, -4, -3, -2, -1, 0, 1, 2, 3, 4, -4, -3, -2, \
-1, 0, 1, 2, 3, 4, -4, -3, -2, -1, 0, 1, 2, 3, 4, -4, -3, -2, -1, 0, \
1, 2, 3, 4, -4, -3, -2, -1, 0, 1, 2, 3, 4, -4, -3, -2, -1, 0, 1, 2, \
3, 4, -4}

In[160]:= {%157, %158} // Transpose

Out[160]= {{-4, -4}, {-4, -3}, {-4, -2}, {-4, -1}, {-4, 0}, {-4, 
  1}, {-4, 2}, {-4, 3}, {-4, 
  4}, {-3, -4}, {-3, -3}, {-3, -2}, {-3, -1}, {-3, 0}, {-3, 1}, {-3, 
  2}, {-3, 3}, {-3, 4}, {-2, -4}, {-2, -3}, {-2, -2}, {-2, -1}, {-2, 
  0}, {-2, 1}, {-2, 2}, {-2, 3}, {-2, 
  4}, {-1, -4}, {-1, -3}, {-1, -2}, {-1, -1}, {-1, 0}, {-1, 1}, {-1, 
  2}, {-1, 3}, {-1, 4}, {0, -4}, {0, -3}, {0, -2}, {0, -1}, {0, 
  0}, {0, 1}, {0, 2}, {0, 3}, {0, 
  4}, {1, -4}, {1, -3}, {1, -2}, {1, -1}, {1, 0}, {1, 1}, {1, 2}, {1, 
  3}, {1, 4}, {2, -4}, {2, -3}, {2, -2}, {2, -1}, {2, 0}, {2, 1}, {2, 
  2}, {2, 3}, {2, 4}, {3, -4}, {3, -3}, {3, -2}, {3, -1}, {3, 0}, {3, 
  1}, {3, 2}, {3, 3}, {3, 4}, {4, -4}, {4, -3}, {4, -2}, {4, -1}, {4, 
  0}, {4, 1}, {4, 2}, {4, 3}, {4, 
  4}, {5, -4}, {5, -3}, {5, -2}, {5, -1}, {5, 0}, {5, 1}, {5, 2}, {5, 
  3}, {5, 4}, {6, -4}, {6, -3}, {6, -2}, {6, -1}, {6, 0}, {6, 1}, {6, 
  2}, {6, 3}, {6, 4}, {7, -4}}

2015년 8월 21일 금요일

2015년 8월 17일 월요일

line land fuel



입력으로 벡터와 그 벡터 내의 인덱스를 주면, 해당 인덱스와 다른 모든 원소들간의 거리를 구해서 그 min값과 max값을 보여주는 프로그램.
예를들어,

std::vector<int> b({-5,-2,2,7});
a = LineLandFuel(0, b);

이렇게 주면 b의 0번째 원소인 -5와 나머지 원소들간의 차 중에 가장 큰것(12)과 작은것(3)을 반환하면 된다. 입력은 항상 정렬되어 있다.

아래는 1위 작품. 이번에도 역시 매일 우승하던 오렌지프로필을 가진 그친구다.

int x, y=1e9;
template <class T>
T shortest(int i, T a) {
for(int v: a) v=abs(a[i]-v), x>v?:x=v, y<v|!v?:y=v;
return { x, y };
}


(1) 난 INT_MAX를 썼는데 1e9를 썼다. 이건 약간 lucky하게 test case를 통과한것 아닌가 싶다.
(2) 템플릿함수는 리턴타입이나 인자만으로 추정해서 부를 수 있나보다. 위의 함수는 다음과 같이 그냥 부를수 있다.

std::vector<int> a, b({-5,-2,2,7});
 a = shortest(0,b);

 또 하나 배웠다. 함수 선언까지 코드 길이에 포함되므로 리턴타입과 받는 인자가 std::vector<int> 같은 긴 이름일때 매우 유용할듯 하다. 실제 업무에 쓸일은 있을까 싶지만.
(3) 작성하면서 min값을 판별할 때 자기 자신과의 차(0)는 어떻게 제외할까 고민했었는데 저렇게 간단히(y<v|!v?:y=v)해결되는 것이었다. 이것과 관련해 의문이 생겨서 stackoverflow에 질문을 했다가 몇개 또 배웠다.
(3-1) ternary operator에서 true-expression을 생략하는 것은 warning이지만, false-expression을 생략하면 error다. 이건 gcc extension이다. a?:ya?a:y와 같다. 이 둘의 차이는 a가 한번 evaluation되느냐 두번 evaluation되느냐 이다.
(3-2) a|!b!a&b는 다를 수 있다. bool로 conversion이 되다 안되다 할 수 있다. 위 질문링크에 y=3, v=2일 때, y>v|!vy<v&v가 값이 같다는 답글이 있다.
(4) comma로 expression을 계속 잇는 것과 ternary operator에 익숙하면 타이핑을 많이 절약할 수 있을 것 같다.
(5) v도 한번 재활용 되었다.

find primes

https://codefights.com/challenge/ZbGabd7jjYHRqePHy

std::vectorint > rPrimeNumbers(int aint b) {
  for(int i; i=a<=b; i==a++?r.push_back(i),0:0)
    for(; ++i<a&&a%i; );
  return r;
}

정말 타고 나긴 타고 나나 보다.
약간 보기 좋게 바꾸면,

std::vector<int> PrimeNumbers(int a, int b) {
  for(int i; i=a<=b;)
    {
      for(; ++i<a&&a%i; )
{
          //skip non-prime numbers                                                                                                              
}
      if(i==a++) {
r.push_back(i);
      }
    }
  return r;

}

선언은 내 gcc로는 에러나는데 codefight에서는 되는것 같다. 여튼간에,
받은 변수(a)를 잘 이용해서 새로운 변수를 선언하지 않는 것이나,  전위, 후위 연산자를 적절하게 이용하는 것, for문을 잘 이용하는 것등은 익숙한데,  i==a++?r.push_back(i),0:0 이거 하나 더 배웠다. expression을 만들기 위해 0을 넣다니.

i는 종료조건에 다다르기 전까지 무조건 1에서부터 시작하고(그렇지 않다면 0으로 for가 종료된다) for문 처음에 ++i가 있어서 1을 제외하는 문제는 자연스럽게 해결된다. (1은 소수가 아니니까 제외해야 한다). 목표점(a)에 다다를때까지 어떤 숫자로도 나눠지지 않으면 소수이고, 마지막에 a++때문에 b에 도달할때까지 차례로 모든 수를 검사하게 된다.






2015년 8월 6일 목요일

sum of 3’s or 5’s multiples

숫자 입력 N보다 작거나 같은 수 중에 3의 배수이거나 5의 배수인 수를 모두 합하는 프로그램.
codefights.com에서 본 것인데 shortest code가 정말 예술이다.

int s,Sum_Of_Multiples_3_Or_5(int N) {
for(;N--;)
      N%3 * N%5 ?:s+=N;
   return s;
}

아름답다.

2015년 7월 24일 금요일

생각할수록

아직 아는게 너무너무 적지만,
생각할수록 딥러닝은 멍청한 짓인것 같다.
template matching + clustering 이 인식의 답일것 같고, (이 ‘답’을 이루는 수학적 재료들은 이미 다 나와 있는 것이 아닐까. 딥러닝을 해낼 수 있는 수학 말고.)
여기에 bayesian 결합하면 ‘생각’을 흉내낼 수 있을 것 같다.

그리고 계속 노력하면 작은 것이라도 할 수 있으리라는 확신이 점점 더 강하게 든다.


I think Deep Learning is not the solution of recognition or detection, absolutely same to AI. Surely this can be wrong. I think ‘template matching + clustering’ is the solution that everyone is finding, and AI can be achieved by this plus ‘bayesian’. This may be something like the ‘intelligence’.

And, if I do my best steadily, I can make something someday even that is very small thing. I became to gain confidence.

2015년 7월 15일 수요일

OpenCV cmake with cuda. (at linux)

$ mkdir build
$ cd build
$ cmake -D CMAKE_BUILD_TYPE=RELEASE -D CMAKE_INSTALL_PREFIX=/where/you/want -D CUDA_GENERATION=Auto ..

2015년 7월 2일 목요일

join every 2 lines in a file

http://www.theunixschool.com/2012/03/join-every-2-lines-in-file.html


훌륭하다 훌륭해.
$ paste - - -d, < file
$ paste -s -d",\n" file
$ sed 'N;s/\n/,/' file
$ perl -pne 'if($.%2){s/\n/,/;}' file
$ xargs -L 2 < file | awk '$1=$1' OFS=,
$ awk 'NR%2{printf "%s,",$0;next}{print;}' file

2015년 6월 30일 화요일

다른 리소스를 필요로 하는 프로그램

 어떤 프로그램은 다른 리소스를 필요로 한다. 예를 들어 face detector는 model file이 필요하다(물론 그렇지 않은 detector도 있다). 얼굴에 대한 정보를 가지고 있는 model file이 있어야 target image에서 얼굴을 잡아낼 수 있다. OpenCV가 제공하는 face detector의 경우 xml파일이 이에 해당한다.
 팀 내에서 프로젝트를 하는데 이 model파일을 찾아내서 사용하는 프로그램을 넘겨받았다. 환경변수를 다 뒤져서 그 경로마다 해당 파일이 있는지 확인하고 있으면 사용한다. 이런 짓은 이식성에 도움을 주기는 커녕 사용하는 사람들을 혼란에 빠트릴 뿐이다. 프로그램이 현재 실행되는 디렉토리에서 찾아보든지 아니면 실행시 argument로 file을 명시적으로 지정하게 해야 한다. 그 외에는 에러를 주고 멈추면 되는 것이다.
 쓸데없는 노력으로 자신의 자부심나무에만 열심히 물을 주고 주변 모든 사람들을 괴롭게 만드는 사람들이 어디에나 있다.


 Some program needs other resources to run. For example, OpenCV's face detector needs an xml file which includes model data about face. It finds faces using this model.
 If one writes a program like this, there is no need to make the program find everywhere possible to find that xml file. Just find 'current' directory or get an argument that specifies the xml path. If it can not find an xml file, just stop to run with a generous error. My co-worker writes a program that finds everywhere possible using environment variables. If it runs well that way, it is more harmful more than not running. If the program stops or runs problematic way with the xml file problem, a user would not know where is errornous.

2015년 5월 21일 목요일

grep: count total number of occurrences

원출처는 http://unix.stackexchange.com/questions/6979/grep-count-total-number-of-occurrences


파일안에 특정 스트링이 총 몇번 나오는지 세려고 -c옵션을 쓰면, 해당 스트링을 포함하는 라인수만 나온다. 예를 들어 라인은 하나인데(\n이 딱 하나 들어있는데) 스트링은 수천만자에 달하는 긴 스트링에 대해 grep -c string 하면 1만 나온다는 뜻.

-o 옵션과 wc 명령을 섞어 쓴다.
grep -o string filename | wc -l

-o
--only-matching
Print only the matched (non-empty) parts of matching lines, with each such part on a separate output line. 

2015년 4월 14일 화요일

‘도은이 아빠’네

확실하지는 않지만 아마
‘도은이 아빠’라고 불리는 분의 블로그인것 같다.
http://doeun.blogspot.kr
요즘도 조판에 열심이신가보다.
한국에서 \(\LaTeX\)을 접하는 사람이라면 누구나 한번쯤 접해보았을 그 이름.

 작정하고 파고들 기회도 없었지만, 계속 다루다보면 어느정도 감이 생길법도 한데 아직도 어떤 원리나 구조로 \(\TeX\)이 동작하는지, 한글을 가능하게 한 노고는 어디에서 비롯된 것인지 대강도 이해하지 못한다. 아마 앞으로도 그럴 것 같다. 그래서 한번 만나뵌적도 없지만 존경하게 되는 것 같다. 교수님이시라는 얘기도 있던데. 검색해봐도 KTUG의 무수한 질문과 답변글 뿐, 흔한 뉴스기사 한토막 안나온다.

2015년 3월 25일 수요일

tiff로 스캔받은것 pdf로 변환

처음부터 pdf로 받으면 되는데 사정상 이리 됨.


150메가정도 되는 multi page tiff file을 pdf로 변환하려고 하는데 적당한 툴을 못찾겠다.
웹에서 무료변환해주는 사이트나 툴이 몇개 있는데 두세개 해보니 모두 메모리 부족.
(총 104페이지로 분량이 많은건 아닌데 full color가 들어있어서 중간에 메모리가 많이 필요한것 같았다. 하나씩 분리한 뒤 보니 가장 큰 페이지가 22M정도.)
acrobat XI pro 로 한번에 import 한 뒤 변환하려 했는데 이것도 에러남.




tiff를 하나씩 split한 다음 다시 pdf로 합하는 방법을 쓰기로 했다.
tiff splitter만 성공했다. 다른것들은 모두 메모리 부족. imagemagick도 받아서 convert를 썼는데 역시 메모리 부족이었다.


이렇게 해서 다 나누고 나니 페이지가 돌아가 있어서 바로 돌리고,
 for i in {3..104}; do  convert page\ \($i\).tif -rotate 270 p$i.tif ; done

이제 acrobat XI에서 모두 import하면 pdf를 얻는다.

pdf에서 한쪽이 다음과 같은 모양이어서,


split.py를 이용해 pdf의 각 페이지를 자른다.
(이게 출처가 기억이 안남..)

(split.py 코드)
import copy
import math
import pyPdf

def split_pages(src, dst):
src_f = file(src, 'r+b')
dst_f = file(dst, 'w+b')

input = pyPdf.PdfFileReader(src_f)
output = pyPdf.PdfFileWriter()

for i in range(input.getNumPages()):
p = input.getPage(i)
q = copy.copy(p)
q.mediaBox = copy.copy(p.mediaBox)

x1, x2 = p.mediaBox.lowerLeft
x3, x4 = p.mediaBox.upperRight

x1, x2 = math.floor(x1), math.floor(x2)
x3, x4 = math.floor(x3), math.floor(x4)
x5, x6 = math.floor(x3/2), math.floor(x4/2)

if x3 > x4:
# horizontal
p.mediaBox.upperRight = (x5, x4)
p.mediaBox.lowerLeft = (x1, x2)

q.mediaBox.upperRight = (x3, x4)
q.mediaBox.lowerLeft = (x5, x2)
else:
# vertical
p.mediaBox.upperRight = (x3, x4)
p.mediaBox.lowerLeft = (x1, x6)

q.mediaBox.upperRight = (x3, x6)
q.mediaBox.lowerLeft = (x1, x2)

output.addPage(p)
output.addPage(q)

output.write(dst_f)
src_f.close()
dst_f.close()


그럼 끝.