《算法》第三章部分程序 part 1
▶ 书中第三章部分程序,加上自己补充的代码,包括单词频率统计,(单链表)顺序查找表,二分查找表
● 单词频率统计
package package01; import edu.princeton.cs.algs4.StdIn;
import edu.princeton.cs.algs4.ST;
import edu.princeton.cs.algs4.StdOut; public class class01
{
private class01() {} public static void main(String[] args)
{
int distinct = 0, words = 0;
int minlen = Integer.parseInt(args[0]); // 第一个参数,参与统计的单词长度下限
ST<String, Integer> st = new ST<String, Integer>(); for(;!StdIn.isEmpty();)
{
String key = StdIn.readString();
if (key.length() < minlen) // 过短的单词不参与处理
continue;
words++;
if (st.contains(key)) // 已有就计数 +1,没有就新添记录
st.put(key, st.get(key) + 1);
else
{
st.put(key, 1);
distinct++;
}
} String max = ""; // 迭代器遍历符号表,查找频率最高的单词
st.put(max, 0);
for (String word : st.keys())
{
if (st.get(word) > st.get(max))
max = word;
}
StdOut.println(max + " " + st.get(max));
StdOut.println("distinct = " + distinct);
StdOut.println("words = " + words);
}
}
● (单链表)顺序查找表
package package01; import edu.princeton.cs.algs4.Queue;
import edu.princeton.cs.algs4.StdIn;
import edu.princeton.cs.algs4.StdOut; public class class01<Key, Value>
{
private int n;
private Node first; private class Node
{
private Key key;
private Value val;
private Node next; public Node(Key inputKey, Value inputVal, Node inputNext)
{
key = inputKey;
val = inputVal;
next = inputNext;
}
} public class01() {} public int size()
{
return n;
} public boolean isEmpty()
{
return size() == 0;
} public boolean contains(Key key) // 判断是否存在键 key
{
if (key == null)
throw new IllegalArgumentException("\n<contains> key == null.\n");
return get(key) != null;
} public Value get(Key key) // 查询元素的值
{
if (key == null)
throw new IllegalArgumentException("\n<get> key == null.\n");
for (Node x = first; x != null; x = x.next)
{
if (key.equals(x.key))
return x.val;
}
return null;
} public void put(Key key, Value val) // 插入元素
{
if (key == null)
throw new IllegalArgumentException("\n<put> key == null.\n");
if (val == null) // 空值用于删除
{
delete(key);
return;
}
for (Node x = first; x != null; x = x.next)
{
if (key.equals(x.key))
{
x.val = val;
return;
}
}
first = new Node(key, val, first);
n++;
} public void delete(Key key) // 删除元素
{
if (key == null)
throw new IllegalArgumentException("\n<delete> key == null.\n");
first = deleteKernel(first, key);
} private Node deleteKernel(Node x, Key key) // 删除元素的递归内核
{
if (x == null)
return null;
if (key.equals(x.key)) // x 头节点的键等于 key
{
n--;
return x.next;
}
x.next = deleteKernel(x.next, key); // 递归删除目标节点,需要用栈保存从链表开头到目标节点之间的所有节点
return x;
} public Iterable<Key> keys() // 将单链表依次入队,构成迭代器
{
Queue<Key> queue = new Queue<Key>();
for (Node x = first; x != null; x = x.next)
queue.enqueue(x.key);
return queue;
} public static void main(String[] args)
{
class01<String, Integer> st = new class01<String, Integer>();
for (int i = 0; !StdIn.isEmpty(); i++)
{
String key = StdIn.readString();
st.put(key, i);
}
for (String s : st.keys())
StdOut.println(s + " " + st.get(s));
}
}
● 二分查找表
package package01; import java.util.NoSuchElementException;
import edu.princeton.cs.algs4.Queue;
import edu.princeton.cs.algs4.StdIn;
import edu.princeton.cs.algs4.StdOut; public class class01<Key extends Comparable<Key>, Value>
{
private Key[] keys;
private Value[] vals;
private int n = 0; public class01()
{
this(2); // 省缺初始尺寸为 2
} public class01(int capacity)
{
keys = (Key[]) new Comparable[capacity];
vals = (Value[]) new Object[capacity];
} private void resize(int capacity) // 尺寸扩展为 capacity
{
assert capacity >= n;
Key[] tempk = (Key[]) new Comparable[capacity];
Value[] tempv = (Value[]) new Object[capacity];
for (int i = 0; i < n; i++)
{
tempk[i] = keys[i];
tempv[i] = vals[i];
}
vals = tempv;
keys = tempk;
} public int size()
{
return n;
} public boolean isEmpty()
{
return size() == 0;
} public boolean contains(Key key)
{
if (key == null)
throw new IllegalArgumentException("\n<contains> key == null.\n");
return get(key) != null;
} public Value get(Key key)
{
if (key == null)
throw new IllegalArgumentException("\n<get> key == null.\n");
if (isEmpty())
return null;
int i = rank(key);
if (i < n && keys[i].compareTo(key) == 0)
return vals[i];
return null;
} public int rank(Key key) // 二分搜索
{
if (key == null)
throw new IllegalArgumentException("\n<rank> key == null.\n");
int lo = 0, hi = n - 1;
for (; lo <= hi;)
{
int mid = lo + (hi - lo) / 2;
int cmp = key.compareTo(keys[mid]);
if (cmp < 0)
hi = mid - 1;
else if (cmp > 0)
lo = mid + 1;
else return mid;
}
return lo;
} public void put(Key key, Value val)
{
if (key == null)
throw new IllegalArgumentException("\n<put> key == null.\n");
if (val == null)
{
delete(key);
return;
}
int i = rank(key);
if (i < n && keys[i].compareTo(key) == 0)
{
vals[i] = val;
return;
}
if (n == keys.length)
resize(2 * keys.length);
for (int j = n; j > i; j--)
{
keys[j] = keys[j - 1];
vals[j] = vals[j - 1];
}
keys[i] = key;
vals[i] = val;
n++;
//assert check();
} public void delete(Key key)
{
if (key == null)
throw new IllegalArgumentException("\n<delete> key == null.\n");
if (isEmpty())
return;
int i = rank(key);
if (i == n || keys[i].compareTo(key) != 0)
return;
for (int j = i; j < n - 1; j++) // 删除节点时要依次挪动
{
keys[j] = keys[j + 1];
vals[j] = vals[j + 1];
}
n--;
keys[n] = null; // 方便垃圾回收
vals[n] = null;
if (n > 0 && n == keys.length / 4)
resize(keys.length / 2);
//assert check();
} public void deleteMin()
{
if (isEmpty())
throw new NoSuchElementException("\n<deleteMin> underflow.\n");
delete(min());
} public void deleteMax()
{
if (isEmpty())
throw new NoSuchElementException("\n<deleteMax> underflow.\n");
delete(max());
} public Key min()
{
if (isEmpty())
throw new NoSuchElementException("\n<min> empty.\n");
return keys[0];
} public Key max()
{
if (isEmpty())
throw new NoSuchElementException("\n<max> empty.\n");
return keys[n - 1];
} public Key select(int k)
{
if (k < 0 || k >= size())
throw new IllegalArgumentException("\n<select> k < 0 || k >= size.\n");
return keys[k];
} public Key floor(Key key) // 返回 key 的上一个元素
{
if (key == null)
throw new IllegalArgumentException("\n<floor> key == null.\n");
int i = rank(key);
if (i < n && key.compareTo(keys[i]) == 0)
return keys[i];
if (i == 0)
return null;
else return keys[i - 1];
} public Key ceiling(Key key) // 返回 key 的下一个元素
{
if (key == null)
throw new IllegalArgumentException("\n<ceiling> key == null.\n");
int i = rank(key);
if (i == n)
return null;
else return keys[i];
} public int size(Key lo, Key hi) // 返回 lo 到 hi 的元素个数
{
if (lo == null)
throw new IllegalArgumentException("\n<size> lo == null.\n");
if (hi == null)
throw new IllegalArgumentException("\n<size> hi == null.\n");
if (lo.compareTo(hi) > 0)
return 0;
return rank(hi) - rank(lo) + (contains(hi) ? 1 : 0); } public Iterable<Key> keys()
{
return keys(min(), max());
} public Iterable<Key> keys(Key lo, Key hi)
{
if (lo == null)
throw new IllegalArgumentException("\n<keys> lo == null.\n");
if (hi == null)
throw new IllegalArgumentException("\n<keys> lo == null.\n");
Queue<Key> queue = new Queue<Key>();
if (lo.compareTo(hi) > 0)
return queue;
for (int i = rank(lo); i < rank(hi); i++)
queue.enqueue(keys[i]);
if (contains(hi))
queue.enqueue(keys[rank(hi)]);
return queue;
} private boolean check()
{
for (int i = 1; i < size(); i++)
{
if (keys[i].compareTo(keys[i - 1]) < 0)
return false;
}
for (int i = 0; i < size(); i++)
{
if (i != rank(select(i)))
return false;
}
for (int i = 0; i < size(); i++)
{
if (keys[i].compareTo(select(rank(keys[i]))) != 0)
return false;
}
return true;
}
public static void main(String[] args)
{
class01<String, Integer> st = new class01<String, Integer>();
for (int i = 0; !StdIn.isEmpty(); i++)
{
String key = StdIn.readString();
st.put(key, i);
}
for (String s : st.keys())
StdOut.println(s + " " + st.get(s));
}
}
《算法》第三章部分程序 part 1的更多相关文章
- 《算法》第三章部分程序 part 6
▶ 书中第三章部分程序,加上自己补充的代码,包含双向索引表.文建索引.稀疏向量类型 ● 双向索引表 package package01; import edu.princeton.cs.algs4.S ...
- 《算法》第三章部分程序 part 5
▶ 书中第三章部分程序,加上自己补充的代码,包含公共符号表.集合类型 ● 公共符号表,用于普通查找表的基本类 package package01; import java.util.NoSuchEle ...
- 《算法》第三章部分程序 part 4
▶ 书中第三章部分程序,加上自己补充的代码,包括散列表.线性探查表 ● 散列表 package package01; import edu.princeton.cs.algs4.Queue; impo ...
- 《算法》第三章部分程序 part 3
▶ 书中第三章部分程序,加上自己补充的代码,红黑树 ● 红黑树,大部分方法与注释与二叉树相同 package package01; import java.util.NoSuchElementExce ...
- 《算法》第三章部分程序 part 2
▶ 书中第三章部分程序,加上自己补充的代码,平衡二叉搜索树 ● 平衡二叉搜索树 package package01; import java.util.NoSuchElementException; ...
- 《算法》第二章部分程序 part 3
▶ 书中第二章部分程序,加上自己补充的代码,包括各种优化的快排 package package01; import edu.princeton.cs.algs4.In; import edu.prin ...
- 《算法》第一章部分程序 part 1
▶ 书中第一章部分程序,加上自己补充的代码,包括若干种二分搜索,寻找图上连通分量数的两种算法 ● 代码,二分搜索 package package01; import java.util.Arrays; ...
- 《算法》第二章部分程序 part 5
▶ 书中第二章部分程序,加上自己补充的代码,包括利用优先队列进行多路归并和堆排序 ● 利用优先队列进行多路归并 package package01; import edu.princeton.cs.a ...
- 《算法》第二章部分程序 part 4
▶ 书中第二章部分程序,加上自己补充的代码,包括优先队列和索引优先队列 ● 优先队列 package package01; import java.util.Comparator; import ja ...
随机推荐
- msp430学习笔记-USART
本文引用:http://bbs.ednchina.com/BLOG_ARTICLE_3013784.HTM MSP430F149有两个USART通讯端口,其性能完全一样,每个通讯口可通过RS232和R ...
- OpenEXR的输出机制
最近在一直在研究OpenEXR这个软件.这个软件的图像输出机制很有意思,特地分享一下学习心得,就当是笔记了. 我的OpenEXR软件版本是2.2.0,系统平台是win7. 安装完毕OpenEXR之后我 ...
- tomcat整体架构
1.背景 Tomcat作为JavaWeb领域的Web容器,目前在我们淘宝也使用的也非常广泛,现在基本上所有线上业务系统都是部署在Tomcat上.为了对平时开发的Web系统有更深入的理解以及出于好奇心对 ...
- 浏览器唤起APP的功能
http://blog.html5funny.com/2015/06/19/open-app-from-mobile-web-browser-or-webview/ http://panli.mu.g ...
- ASP.NET重写Render 加载CSS样式文件和JS文件(切换CSS换皮肤)
网页换皮肤的方式有很多种,最简单的通常就是切换页面CSS,而CSS通常写在外部CSS文件里.那么切换CSS其实就是更换html里的link href路径.我在网上搜索了下. 一般有两种方式: 1.页面 ...
- JS之滚动条效果2
在前面一篇说的是滚动条效果,本篇继续在前面的基础上面针对滚动条进行操作.本次要实现的效果如下:拖动滚动条左右移动时,上面的图片内容也相对外层盒子做相对移动. 下面针对要实现的效果进行分析:首先是页面基 ...
- chrome 抓包的小功能--preserve log (记录页面跳转后,所有的抓包记录)
1.记录页面跳转后,所有的抓包记录,勾上
- [转][html]radio 获取选中状态
方法一: if ($("#checkbox-id").get(0).checked) { // do something } 方法二: if($('#checkbox-id').i ...
- [C#][WebAPI]返回 json
//将webapi的返回值设为Json格式 var jsonFormatter = new JsonMediaTypeFormatter(); GlobalConfiguration.Configur ...
- 【原创】虚拟机上实现绑定固定IP扩主机容器互访
Docker绑定固定IP/跨主机容器互访 https://blog.csdn.net/qq_34021712/article/details/75948566 服务器IP 容器分配网段 启动容 ...