카운트 & top-n 소트 알고리즘
글쓴이: spacelee / 작성시간: 월, 2005/11/28 - 5:14오후
지금 제가 고민하고 있는 문제입니다.
ex)
어떤 문서에 포함된 단어들에 대해 counting을 한다.
counting이 끝나면 count에 대해 소팅하여
top-n 개의 소팅된 단어를 구한다.
제 생각은 간단하게 counting은 해쉬를 써서,
top-n은 heapsort를 쓰면 되지 않을까 싶은데
각각에 대해 더 좋은 솔루션이 있는지 궁금합니다.
또, 별개로 처리하는 것이 아니라
두 문제를 연계하여 Cpu나 메모리를 효율적으로
사용하면서 처리할 수 있는 좋은 알고리즘방식이 있는지
궁금합니다.
비슷한 문제를 고민하신 분들이 많이 계셨을것 같은데
도움 부탁드립니다.^^
File attachments:
첨부 | 파일 크기 |
---|---|
finding_median1.pdf | 81.1 KB |
Forums:
상위 n개 단어를 구할 때 (단어의 개수를 N이라고 하면) heapsor
상위 n개 단어를 구할 때 (단어의 개수를 N이라고 하면) heapsort를 하면 O(N log N) + O(n log N) = O(N log N)이 됩니다.
좀더 단순한 방법을 쓰는 건 어떨까요? n개 크기의 배열을 만들고 여기에 '현재까지 순회한 item 중 상위 n개의 item'을 '내림차순으로' 저장하는 겁니다. N개 항목을 순회하면서 매번 O(n)의 연산을 수행하게 되므로 전체 시간복잡도는 O(N * n)이 됩니다. n이 그리 크지 않고 N과 별 관계가 없다면 이 방법이 더 효율적일 수 있습니다. 구현도 더 간단할 거구요.
이 방법을 쓰면 counting과 sorting을 동시에 수행할 수도 있습니다. hash table node를 추가/갱신하면서 n개짜리 배열에서의 순위를 조절해주면 되니까요.
뭔가... 그림도 없고 코드도 없이 말로만 표현하자니 허전하기가 그지없습니다만... 후다닥 :arrow:
$PWD `date`
[quote="wariua"]상위 n개 단어를 구할 때 (단어의 개수를
아 정말 좋은 아이디어 같습니다.^^
순위조절할때는 버블소트처럼 해당 아이템만
이동해주면 되겠네요.
그럼 practical하게는 O(n)까지 안가도 될것 같네요.
감솨감솨~^^
아 그리고 하나 더 여쭤보고 싶은것이top-n sort만 하려면
아 그리고 하나 더 여쭤보고 싶은것이
top-n sort만 하려면
어떤 소팅 방법이 가장 좋을까요?
logN = n10^ n = NO(N log N)와 O(N*n
logN = n
10^ n = N
O(N log N)와 O(N*n) 의 비교라고 하면..
logN <= n 이면, 그냥 힙소팅을 하는게 좋고
아니라면 wariua님의 방식이 좋은것이되겠군요..
일반적으로는 힙소팅으로 하는 것이 성능이 좋을듯 한데,
메모리 효율을 생각하면 힙소팅이 더 나쁠수도 있을것 같네요..
logN = n 일경우 10^n = N 이므로 계산은 어렵지 않을듯합니다.
저도 예전에 이런 비슷한 연산 프로그램을 잠깐 만들어본적이 있는데
미디언 값을 찾는 알고리즘이었습니다.
저 같은 경우에는 quick sort 를 사용해서 구현했는데
(quick sort 도 NlogN 입니다)
앞서의 힙소팅 보다 메모리 효율성을 높일 수 있는 방법이 있습니다.
quick sort의 경우 각 루프 마다
특정 피봇 값을 기준으로 큰 것들과 작은 것들을 걸러내 주고
다음 루프는 좌우에 대해 각각 리커시브하게 동작하게 되어있죠.
(말로 설명이 좀 어렵지만;;; 퀵소트 다들 아실꺼라 생각하니...)
이 경우 자신의 원하는 값이 포함된 쪽으로만 계속 리커시브를 타고
반대쪽은 그냥 버리면 됩니다...
참고되시길..
*PS:박사 과정에 있는 형에게 얘기 했더니 제가 생각한것보다 더 좋은 미디언 구하는 방식이 있다고 하는데... 그냥 가르쳐주지는 않더군요. 아직 고민중입니다;;;
일하는 사람들의 희망 민주노동당 : http://www.kdlp.org
반공 교육의 성과로, 민주주의의 반대가 공산주의(또는 사회주의)라고 생각하는 사람이 많다.
혹시 도움이 될까 하고 예전에 만들었던것을 올려봅니다.미디언 구하는
혹시 도움이 될까 하고 예전에 만들었던것을 올려봅니다.
미디언 구하는 것이기 때문에
조금 고쳐서 사용하셔야 할것 같습니다..
그리고 앞뒤 내용으로 짐작하건데 모바일같은 환경에서 C를 사용하실것 같은데;;
불행히도 제가 만든건 C++이네요;;;
일하는 사람들의 희망 민주노동당 : http://www.kdlp.org
반공 교육의 성과로, 민주주의의 반대가 공산주의(또는 사회주의)라고 생각하는 사람이 많다.
[quote="쌀밥"]혹시 도움이 될까 하고 예전에 만들었던것을 올려봅니
답변 감솨감솨~^^
많은 도움이 되었습니다.^^
그나저나 박사과정 형님은 치사하시네여 ㅋㅋ
권위를 의심할 것,어긋남을 존경할 것,자리잡기를 거부할 것,항상 자신을 재창조할 것 - MIT 미디어랩 -
[quote="쌀밥"]logN = n10^ n = NO(N l
제가 다른 자료 찾다가 우연히 찾은 논문인데요.
좋은 아이디어인지는 모르겠지만 한번 참고해보세요.
읽어보시고 코멘트 부탁드려용.~ ^^;;
권위를 의심할 것,어긋남을 존경할 것,자리잡기를 거부할 것,항상 자신을 재창조할 것 - MIT 미디어랩 -
[quote="spacelee"][quote="쌀밥"]logN = n
아마 그 박사과정분이 생각하시는 게 이게 맞을 거 같습니다. 3.3절에서 다루는 알고리즘이 최악의 경우에도 O(N)에 k번째 수를 찾아주는 알고리즘입니다.
뒷쪽의 증명하는 부분은 보지 않았습니다. 3.3절까지만 보면 대충 전
뒷쪽의 증명하는 부분은 보지 않았습니다.
3.3절까지만 보면 대충 전체 내용을 알수 있는것 같습니다.
놀랍게도, (제가 이해한게 맞다면) 3.2 절까지는 제가 사용한 접근방법과 흡사하군요.
셈플링 key 중에서 미디언을 잡아서 나머지와 비교해본뒤
실제 미디언임이 밝혀지면 끝나고
아니면, 이 값보다 크거나 작은 쪽은 고려 대상에서 제외시키는 방법입니다.
3.3 절에서 설명하고 있는 것은
여기에서 좀 더 나가서,
후보 선택 방법을, '후보중의 후보'로 선택해서 정확도를 높이는 방법인데...
앞의 제 quick-sort의 경우로 얘기를 하자면, 피봇 값을 임의로 정하지 말고
좀 더 효율적인 방법으로 정하면 된다는 것이군요...
여기까지 제가 맞게 이해한건지 우선.. 확신이 좀 없네요;;;
논문의 내용이 심오해서 제가 잘 이해를 못한건지도 모르겠지만,
저는 아무리 곰곰히 생각해봐도, 제가 사용한 quick sort 방식보다
이 논문의 '후보중 후보' 방식을 사용하는게 더 좋아보이질 않습니다.
이글에서 제안하고 있는 '후보중 후보' 방식을 사용하려면
5개(혹은 임의의 홀수)의 임의의 그룹을 만들고
그 안에서 소팅을 하지 않으면 안될것 같은데...
소팅을 하는 것보다는 quick-sort 방식으로 반으로 쪼개 나가는 방식이 더 좋을것 같다는 생각이 듭니다.
뭐, 논문이니, 제가 잘 못 이해했거나, 실제로 해보면 그 방식이 더 좋거나 이겠습니다만... ㅎㅎㅎ
다른분들 생각은 어떠신가요??
일하는 사람들의 희망 민주노동당 : http://www.kdlp.org
반공 교육의 성과로, 민주주의의 반대가 공산주의(또는 사회주의)라고 생각하는 사람이 많다.
댓글 달기