9
A0조 이산치 수학 Project 보고서 조장 : 송하윤 조원 : 조부관 홍진욱 김무경 김도형 장진승

이산치 과제7

  • Upload
    mil23

  • View
    200

  • Download
    0

Embed Size (px)

Citation preview

Page 1: 이산치 과제7

A0조 이산치 수학

Project 보고서

조장 : 송하윤

조원 : 조부관

홍진욱

김무경

김도형

장진승

Page 2: 이산치 과제7

과제수행일지과제수행일지과제수행일지과제수행일지소속 조원

A0 조장 : 송하윤자료조사 및 보고서

작성 : 조부관,김무경,장진승

알고리즘 : 김도형 코딩 : 홍진욱

과제수행기간 5일 6시간

I. 계획의 작성

연구제목 Group codes연구배경

알파뱃을 이진수로 변환하여 압축하는 프로그램을 만들어 압축에 대한

기본적인 원리를 알게 하는 것.

참고자료 참고 URL C로 쓴 자료구조론

II. 계획의 실행

첫째 날 2012년 6월 11일 월요일오늘의 작업 조원의 업무 분담과 학습할 내용 및 과제에 대한 이해와 숙지

토의 내용

조장 : 송하윤알고리즘 : 김도형자료조사 및 보고서 작성 : 김무경, 조부관, 장진승코딩 : 홍진욱

프로젝트를 진행하기에 앞서 그룹코드에 대한 기본적인 이해를 돕기위해 각자 아는 부분에 대하여 논의 하고, 업무 분담을 통하여 부족한 부분에 대한 자료조사와 연구를 하기로함.

둘째 날 2012년 6월 13일 수요일

오늘의 작업

트리 대해 조사해 온 자료 공유 및 회의, 서로 모르는 내용들에 대해 부가적으로 설명을 해주고 프로그램을 구현하는데 필요한 알고리즘에 대해서 조사해오기로 했다.

트리 코딩 참고자료를 보면서 트리에 대한 특징과 구현방법을 익히도록 했다.

토의 내용

알고리즘 알고리즘 알고리즘 알고리즘 설계 설계 설계 설계 기법기법기법기법

■ 알고리즘 설계 기법

• 간단히 효율적인 알고리즘을 구할 수 있는 경우도 있지만 많은 경우 주어진 문제를 해

결하는 알고리즘을 찾는 일이 쉽지 않은 경우가 대부분이다.

• 일반적으로 알려져 있지 않은 새로운 알고리즘을 설계하기 위해서는 여러가지 기법을

동원하게 된다. 단순히 직감적으로 해를 알 수 있는 경우에는 직접 구현하겠지만 대개

의 경우 그렇게 하기는 거의 불가능하고, 설사 가능하다 하더라도 구현에 있어서는 비

효율적이기가 일쑤이다.

• 일반적으로 적용가능한 알고리즘 설계 기법도 많지는 않으나 비교적 단순하면서도 널

리 사용가능한 기법으로 그리디방법(Greedy method), 분할 정복(Divide and

conquer) 그리고 동적 프로그래밍(Dynamic programming)과 선형 프로그래밍(Linear

programming)등이 있다.

허프만코드 허프만코드 허프만코드 허프만코드 개념개념개념개념

■ 허프만코드 : 일종의 파일 압축 알고리즘

• 텍스트에 나타나는 특정 문자에 대한 빈도수를 이용

Page 3: 이산치 과제7

• 자주 사용되는 문자는 짧은 코드를, 자주 사용하지 않는 문자는 긴 코드를 지정

• 실제 평균 문자 코드 길이를 줄여 압축하는 방법

• 파일에 사용되는 문자의 사용빈도가 높은 것은 이진 트리의 높은 위치에, 낮은 것은

이진트리의 낮은 위치에 놓아 코드화

• 허프만 코드는 접두 코드를 회피하여 문자 표현 어떤 코드가 다른 코드의 접두사가 되

지 않으면 코드의 길이는 서로 달라도 문자를 표현하는데 지장 없음

• 이진트리를 생성하여 트리의 왼쪽 종속트리로 갈 때에는 0, 오른쪽 종속트리로 갈 때

에는 1로 코드화

• 허프만 코드는 가장 널리 쓰이는 압축 방법

• 문자가 나타나는 빈도수에 따라 그 크기를 다르게 하는 것 : 빈도수 의존 코드

• 모음과 'L', 'R', 'S', 'N', 'T' 등과 같이 자주 나타나는 문자들은 더 작은 비트를 할당

■ 허프만코드 허프만코드 허프만코드 허프만코드 예제 예제 예제 예제

각각의 확률이 0.5, 0.3, 0.15, 0.05인 4개의 값 x1, ..., x4가 있다고 가정

• 만일 x1, ..., x4값 각각을 나타내기 위해 코드 값 00, 01, 10, 11을 사용한다면 X값

을 전송하기 위해 2비트가 필요

• 그러나 만일 x1을 나타내기 위해 0, x2를 나타내기 위해 10, x3을 나타내기 위해

110, x4를 나타내기 위해 111을 사용한다면, 평균 0.5*1 + 0.3*2 + 0.15*3 + 0.05

* 3 = 1.7비트가 필요

허프만코드 허프만코드 허프만코드 허프만코드 생성 생성 생성 생성 방법방법방법방법

■ 허프만코드 생성 방법

① 단 하나의 노드만을 가지고 있는 이진 트리와 각 문자를 매핑

② 각 트리에 문자들의 빈도수를 할당 : 트리의 가중치(weight) - 내림차순으로 정렬

③ 두 개의 가장 작은 가중치를 가지고 있는 트리를 찾아 하나의 트리로 합치고 새로운 루

트 노드를 만들어 냄 (이 새 트리의 가중치는 합쳐진 두 트리의 가중치의 합)

④ 마지막으로 하나의 트리가 남을 때까지 이 과정을 반복

⑤ 이 과정이 끝났을 때 원래 노드들의 각각은 마지막 이진 트리의 말단 노드(leaf)가 됨

⑥ 이진 트리에서 루트로부터 말단 노드에 이르는 유일한 길(path)이 있게 되고 이 길이 허

프만코드가 됨 ( 각 왼쪽 자식 포인터에 0을 할당하고, 오른쪽 자식 포인터에 1을 할당해서

결정)

과제준비에서

느낀 점

자료조사를 토대로 트리에 대한 개념에 대해 조원별로 토의 하였다. 이 성질을 이용하여 상호참조 생성기를 어떻게 구현할 것인지 크게 구성을 짰으며, 이를 토대로 초안을 작성해 오기로 했다.

셋째 날 2012년 6월 18일 월요일

오늘의 작업작성한 초안에 대한 설명을 듣고 내용을 숙지한 다음, 문제점을 파악한다. 코딩을

완성하여 수정하는 과정을 거친다.

Group

codes

소스

#include <stdio.h>

#include <conio.h>

#include <string.h>

#include <stdlib.h>

#define M 20

typedef struct{

char c;

int ascii;

int cnt;

double avg;

Page 4: 이산치 과제7

}ALP;

typedef struct{

char c;

double avg;

int a[M-1];

int size;

}TEMPA;

/*Function define*/

void initAlp(ALP *a);

void alpPrt(ALP *a, int size);

int alpLen(ALP *a);

void setCnt(ALP *a, int size);

void alpSetAvg(ALP *a,int size);

void sorting(ALP *a, int size);

int sumofCnt(ALP *a, int size);

void initTemp(TEMPA *temp, int size);

void tempaSort(TEMPA *t, int start, int size);

void e();

int main(){

int scanfIndex = 0;

int len = 0, sum = 0;

int i = 0 , j = 0;

/*dynamic alloc*/

ALP *a;

a = (ALP *)malloc(sizeof(ALP)*M);

/*dynamic alloc*/

initAlp(a);

/*initialized root*/

while(1){

(a+scanfIndex)->c = getchar();

(a+scanfIndex)->cnt = 1;

if((a+scanfIndex)->c == 10)

break;

scanfIndex++;

}

/*table length*/

len = alpLen(a);

//printf("%d\n",len);

/* Node Functions

NODE* createNode(NODE *node);

NODE intoNode(NODE *r,NODE *l);

void treePrt(NODE *root);

*/

/*ALP Functions

void initAlp(ALP *a);

void alpPrt(ALP *a);

int alpLen(ALP *a);

void setCnt(ALP *a, int size);

void alpSetAvg(ALP *a,int size);

Page 5: 이산치 과제7

void sorting(ALP *a, int size);

*/

/*1*/

//alpPrt(a, len);

/*2*/

setCnt(a, len);

//alpPrt(a, len);

/*3*/

alpSetAvg(a, len);

//alpPrt(a, len);

/*4*/

sorting(a, len);

//alpPrt(a, len);

sum = sumofCnt(a, len);

/*Create Node*/

TEMPA tempa[sum];

//

TEMPA tempasort[sum];

//

initTemp(tempa,sum);

int tempindex = 0;

for(i = 0 ; i < len ; i++){

if(97 <= (a+i)->c && (a+i)->c <= 122){

tempa[tempindex].c = (a+i)->c;

tempa[tempindex].avg = (a+i)->avg;

for(j = 0 ; j < M - 1; j++){

tempa[tempindex].a[j] = 2;

}

tempindex++;

}

}

e();

for(i = 0 ; i < tempindex ; i++){

printf("%c\t%.2lf",tempa[i].c, tempa[i].avg);

for(j = 0 ; j < M-1 ; j++){

if(tempa[i].a[j] != 2)

printf("[%d]",tempa[i].a[j]);

}e();

}e();

/*

*

* 솔팅 -> 트리 -> 루프

*

*/

int front,rear,sumavg,mid,k;

rear = tempindex - 1;

front = rear - 1;

mid = rear;

sumavg = tempa[i].avg + tempa[i-1].avg;

tempa[rear].avg = sumavg;

tempa[front].avg = sumavg;

for(i = tempindex - 1 ; i > 0 ; i--){

Page 6: 이산치 과제7

if(tempa[i].avg == tempa[i-1].avg){

for(j = front ; j < mid ; j++){

tempa[j].a[tempa[j].size] = 0;

}

for(j = mid ; j <= rear ; j++){

tempa[j].a[tempa[j].size] = 1;

}

for(j = front ; j <= rear ; j++){

tempa[j].size--;

}

mid = front;

front--;

sumavg = 0;

tempaSort(tempa, front, rear);

for(j = front ; j < rear ; j++){

sumavg = sumavg + tempa[j].avg;

}

for(j = front ; j < rear ; j++){

tempa[j].avg = sumavg;

}

}

}

// 여기서 프린트하기전 일단 알파벳 순으로 정렬

int alpa, beta=0;

for(alpa=97;alpa<123;alpa++)

for(i = 0 ; i < tempindex ; i++)

if(tempa[i].c==(char)alpa)

tempasort[beta++]=tempa[i];//정렬부분

// 비정렬부분

for(i = 0 ; i < tempindex ; i++){

printf("%c\tcode =",tempa[i].c);

for(j = 0 ; j < M-1 ; j++){

if(tempa[i].a[j] != 2){

printf("%d",tempa[i].a[j]);

}

}e();

}

printf("\n");

//정렬한거 출력.

for(i = 0 ; i < tempindex ; i++){

printf("%c\tcode =",tempasort[i].c);

for(j = 0 ; j < M-1 ; j++){

if(tempasort[i].a[j] != 2){

printf("%d",tempasort[i].a[j]);

}

}e();

}

getch();

return 0;

}

void tempaSort(TEMPA *t, int start, int size){

int i,j;

TEMPA tm;

TEMPA *temp;

temp = (TEMPA *)malloc(sizeof(TEMPA)*size);

Page 7: 이산치 과제7

temp = &tm;

for(i = size ; i > 0 ; i--){

for(j = 0 ; j < i ; j++){

if((t+j)->avg < (t+j+1)->avg){

temp->avg = (t+j)->avg;

temp->c = (t+j)->c;

(t+j)->avg = (t+j+1)->avg;

(t+j)->c = (t+j+1)->c;

(t+j+1)->avg = temp->avg;

(t+j+1)->c = temp->c;

}

}

}

}

void sorting(ALP *a, int size){

int i,j;

ALP t;

ALP *temp;

temp = (ALP *)malloc(sizeof(ALP)*M);

temp = &t;

for(i = size ; i > 0 ; i--){

for(j = 0 ; j < i ; j++){

if((a+j)->avg < (a+j+1)->avg){

/*change*/

temp->ascii = (a+j)->ascii;

temp->avg = (a+j)->avg;

temp->c = (a+j)->c;

temp->cnt = (a+j)->cnt;

(a+j)->ascii = (a+j+1)->ascii;

(a+j)->avg = (a+j+1)->avg;

(a+j)->c = (a+j+1)->c;

(a+j)->cnt = (a+j+1)->cnt;

(a+j+1)->ascii = temp->ascii;

(a+j+1)->avg = temp->avg;

(a+j+1)->c = temp->c;

(a+j+1)->cnt = temp->cnt;

}

}

}

}

/*average alpha*/

void alpSetAvg(ALP *a,int size){

int i;

for(i = 0 ; i < size ; i++){

(a+i)->avg = (double)(a+i)->cnt/(double)size;

}

}

/*Set alpha*/

void setCnt(ALP *a,int size){

int i,j;

Page 8: 이산치 과제7

for(i = 0 ; i < size - 1 ; i++){

for(j = i + 1 ; j < size ; j++){

if((a+i)->c == (a+j)->c){

(a+i)->cnt++;

(a+j)->c = '\0';

(a+j)->avg = 0;

(a+j)->ascii = 0;

}

}

}

}

/*Length of alpha*/

int alpLen(ALP *a){

int i = 0, ct = 0;

char temp;

temp = (a+i)->c;

while(temp){

if(97 <= temp && temp <= 122){

ct++;

}

i++;

temp = (a+i)->c;

}

return ct;

}

/*initialized*/

void initTemp(TEMPA *temp, int size){

int i,j;

for(i = 0 ; i < size ; i++){

(temp+i)->c = '\0';

(temp+i)->avg = 0;

for(j = 0 ; j < size ; j++){

(temp+i)->size = M-2;

}

}

}

void initAlp(ALP *a){

int i = 0;

for(i = 0 ; i < M ; i++){

(a+i)->ascii = 0;

(a+i)->c = '\0';

(a+i)->cnt = 0;

(a+i)->avg = 0;

}

}

/*Alpha's value*/

int sumofCnt(ALP *a, int size){

int i, result = 0;

for(i = 0 ; i < size ; i++){

if(97 <= (a+i)->c && (a+i)->c <= 122){

result++;

}

}

return result;

}

/*Print*/

void alpPrt(ALP *a, int size){

Page 9: 이산치 과제7

int i = 0;

while(i != size){

if(97 <= (a+i)->c && (a+i)->c <= 122)

printf("%c\t%d\t%.2lf\n",(a+i)->c,(a+i)->cnt,(a+i)->avg);

i++;

}

}

void e(){

printf("\n");

}

III. III. III. III. 결과결과결과결과

최종 프로그램

소스와 설명