simple_huffman 0.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. checksums.yaml +7 -0
  2. data/lib/huffman.rb +95 -0
  3. metadata +58 -0
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 5255ece9e12754b57eb4438695d3322956a72992
4
+ data.tar.gz: e571960c4429e5070e022ce8c07ca4c147dd1836
5
+ SHA512:
6
+ metadata.gz: 4c2d86be3525cdc7b2ec1e1e12287f1370ab6323705e70b80155cc9ab56f58e7baa4f44f45b10b51b242eb2cea8e7f64d4fb07a3bd2b951e9a5cb55afd16c8de
7
+ data.tar.gz: c35a6e624273c8be709c06f19fc3b981ac73e8bf485072f3b43a4c55a0a1c2604eadbc2cc660fa625cbccd90a5a84eb50806e5e9da199b6a2c3c74f6148c922b
data/lib/huffman.rb ADDED
@@ -0,0 +1,95 @@
1
+ class Node
2
+ attr_accessor :value, :weight, :left, :right, :order
3
+ def initialize(value, weight, order=0, left=nil, right=nil)
4
+ @value = value
5
+ @weight = weight
6
+ @left = left
7
+ @right = right
8
+ @order = order #actuality of the node
9
+ end
10
+
11
+ def traverse(code, hash)
12
+ if leaf?
13
+ hash[@value] = code
14
+ else
15
+ @left.traverse(code + '1', hash)
16
+ @right.traverse(code + '0', hash)
17
+ end
18
+ end
19
+
20
+ #the sorting order should be defined by weight and order of the internal node
21
+ #for obtaining Huffman code with minimum variance the most recent internal node should be later in the list
22
+ def <=>(other)
23
+ if @weight < other.weight
24
+ -1
25
+ elsif @weight > other.weight
26
+ 1
27
+ else
28
+ if @order < other.order
29
+ return -1
30
+ elsif @order > other.order
31
+ return 1
32
+ end
33
+ 0
34
+ end
35
+ end
36
+
37
+ def leaf?
38
+ @left.nil? && @right.nil?
39
+ end
40
+ end
41
+
42
+ class Huffman
43
+ # frequencies should be a hash containing the occuring letters of the text and their corresponding frequency
44
+ # i.e. {'a' => 5, 'b' => 3}
45
+ def self.encode(text, frequencies=nil)
46
+ frequencies = get_frequencies(text) unless frequencies
47
+ tree = build_tree(frequencies)
48
+ code_table = {}
49
+ frequencies.size > 1 ? tree.traverse('', code_table) : code_table = {frequencies.keys[0] => '0'}
50
+ {encoded_text: text.chars.map{|char| code_table[char]}.join, code_table: code_table}
51
+ end
52
+
53
+ def self.decode(encoded_text, code_table)
54
+ text = []
55
+ code_table = code_table.invert
56
+ previous = ''
57
+ encoded_text.each_char do |char|
58
+ if code_table[previous + char]
59
+ text << code_table[previous + char]
60
+ previous = ''
61
+ else
62
+ previous += char
63
+ end
64
+ end
65
+ text.join
66
+ end
67
+
68
+ private
69
+ def self.get_frequencies(text)
70
+ frequencies = Hash.new(0)
71
+ text.each_char do |char|
72
+ frequencies[char] += 1
73
+ end
74
+ frequencies
75
+ end
76
+
77
+ def self.build_tree(frequencies)
78
+ nodes = []
79
+ frequencies.each_pair do |letter, frequency|
80
+ nodes << Node.new(letter, frequency)
81
+ end
82
+
83
+ order = 1
84
+ while nodes.length > 1 do
85
+ nodes.sort!
86
+ left = nodes.shift
87
+ right = nodes.shift
88
+ combined = Node.new('', left.weight + right.weight, order, left, right)
89
+ nodes << combined
90
+ order += 1
91
+ end
92
+ nodes.shift
93
+ end
94
+
95
+ end
metadata ADDED
@@ -0,0 +1,58 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: simple_huffman
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.0
5
+ platform: ruby
6
+ authors:
7
+ - Jiayi Zheng
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2014-11-03 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: rspec
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ description: A simple implementation of huffman algorithm
28
+ email: ''
29
+ executables: []
30
+ extensions: []
31
+ extra_rdoc_files: []
32
+ files:
33
+ - lib/huffman.rb
34
+ homepage: https://github.com/thebluber
35
+ licenses:
36
+ - MIT
37
+ metadata: {}
38
+ post_install_message:
39
+ rdoc_options: []
40
+ require_paths:
41
+ - lib
42
+ required_ruby_version: !ruby/object:Gem::Requirement
43
+ requirements:
44
+ - - ">="
45
+ - !ruby/object:Gem::Version
46
+ version: '0'
47
+ required_rubygems_version: !ruby/object:Gem::Requirement
48
+ requirements:
49
+ - - ">="
50
+ - !ruby/object:Gem::Version
51
+ version: '0'
52
+ requirements: []
53
+ rubyforge_project:
54
+ rubygems_version: 2.2.0
55
+ signing_key:
56
+ specification_version: 4
57
+ summary: Huffman encoder/decoder
58
+ test_files: []