public static HuffmanNode HuffmanNode_Create(HuffmanNode other) { return(new HuffmanNode { Character = other.Character, Frequency = other.Frequency, Left = other.Left != null ? HuffmanNode_Create(other.Left) : null, Right = other.Right != null ? HuffmanNode_Create(other.Right) : null, }); }
// Etap III /// <summary> /// Metoda dokonuje dekompresji tekstu skompresowanego metodą Huffmana /// </summary> /// <param name="root">Drzewo Huffmana wykorzystywane do dekompresji</param> /// <param name="encoding">Skompresowany tekst</param> /// <returns>Odtworzony tekst</returns> public string Decompress(HuffmanNode root, BitArray encoding) { if (root == null || encoding == null || encoding.Length == 0) { throw new ArgumentNullException("invalid inputs"); } encoderedString = new StringBuilder(); if (root.Left == null && root.Right == null && encoding.Cast <bool>().Any(x => x == true)) { throw new ArgumentException("incorrect encoding"); } Decode(root, root, encoding, 0); return(encoderedString.ToString()); }
private string AssertNoDuplicatedCharacters(HuffmanNode root) { var visitedCharacters = new SortedSet <char>(); return(NodeVisitor(root, node => { if (node.Character > 0) { if (visitedCharacters.Contains(node.Character)) { return $"{root.Character} was encountered more than once in huffman tree"; } visitedCharacters.Add(node.Character); } return null; })); }
private string AssertNoCircularReferences(HuffmanNode root) { var visitedNodes = new List <HuffmanNode>(); return(NodeVisitor(root, node => { string errorMessage = null; visitedNodes.ForEach(visitedNode => { if (ReferenceEquals(visitedNode, node)) { errorMessage = "Huffman tree contains circular references"; } }); visitedNodes.Add(node); return errorMessage; })); }
public static bool HuffmanNode_Equals(HuffmanNode lhs, HuffmanNode rhs) { if (lhs == null && rhs == null) { return(true); } if (lhs != null && rhs != null) { if (lhs.Character != rhs.Character) { return(false); } if (lhs.Frequency != rhs.Frequency) { return(false); } return(HuffmanNode_Equals(lhs.Left, rhs.Left) && HuffmanNode_Equals(lhs.Right, rhs.Right)); } return(false); }
private string AssertOnlyBaseTextCharacters(HuffmanNode root) { bool[] characters = new bool[char.MaxValue]; foreach (char character in baseText) { characters[character] = true; } return(NodeVisitor(root, node => { if (node.Character > 0) { if (!characters[node.Character]) { return $"Huffman tree should contains only characters that were in base text"; } } return null; })); }
private string AssertTreeStructure(HuffmanNode root) { return(NodeVisitor(root, node => { if (node.Frequency <= 0) { return "Node should have positive frequency"; } if (node.Character == 0) { if (node.Left == null) { return "Non-terminating node (character==0) should have left descendant"; } if (node.Right == null) { return "Non-terminating node (character==0) should have right descendant"; } if (node.Frequency != node.Right.Frequency + node.Left.Frequency) { return "Non-terminating node (character==0) should have frequency equal to sum of descendant frequencies"; } } else { if (node.Left != null) { return $"Leaf node (character='{node.Character}') should not have left descendant"; } if (node.Right != null) { return $"Leaf node (character='{node.Character}') should not have right descendant"; } } return null; })); }
/// <summary> /// Metoda tworzy drzewo Huffmana dla zadanego tekstu /// </summary> /// <param name="baseText">Zadany tekst</param> /// <returns>Drzewo Huffmana</returns> public HuffmanNode CreateHuffmanTree(string baseText) { if (baseText == null || baseText.Length == 0) { throw new ArgumentNullException("invalid string"); } var counter = Counter(baseText); HuffmanPriorityQueue pq = new HuffmanPriorityQueue(); //var orderedCount = counter.OrderBy(x => x.Value); foreach (var c in counter) { var hn = new HuffmanNode(); hn.Character = c.Key; hn.Frequency = c.Value; hn.Left = null; hn.Right = null; pq.Put(hn); } while (pq.Count > 1) { var t1 = pq.Get(); var t2 = pq.Get(); var hn = new HuffmanNode(); hn.Frequency = t1.Frequency + t2.Frequency; hn.Left = t1; hn.Right = t2; pq.Put(hn); } return(pq.Get()); }
private HuffmanNode[] DefineSampleTrees() // 5 drzew { HuffmanNode[] _trees = new HuffmanNode[] { new HuffmanNode { Frequency = 42, Character = 'a' }, // a -> 0; new HuffmanNode { Frequency = 5, Left = new HuffmanNode { Character = 'b', Frequency = 3, }, Right = new HuffmanNode { Character = 'c', Frequency = 2, } }, // b -> 0; c -> 1 new HuffmanNode { Frequency = 11, Left = new HuffmanNode { Character = 'a', Frequency = 5, }, Right = new HuffmanNode { Frequency = 6, Left = new HuffmanNode { Character = 'c', Frequency = 2, }, Right = new HuffmanNode { Character = 'b', Frequency = 4, } } }, // a -> 0; b -> 11; c -> 10; new HuffmanNode { Frequency = 12, Left = new HuffmanNode { Character = 'a', Frequency = 5, }, Right = new HuffmanNode { Character = 'b', Frequency = 7, }, }, // a -> 0; b -> 1 new HuffmanNode { Frequency = 12, Left = new HuffmanNode { Character = 'b', Frequency = 7, }, Right = new HuffmanNode { Character = 'a', Frequency = 5, }, } // a -> 1; b -> 0 }; return(_trees); }
public HuffmanDecompressTestCase(double timeLimit, Exception expectedException, string description, HuffmanNode tree, BitArray encoding, string expectedResult) : base(timeLimit, expectedException, description) { this.tree = tree; this.encoding = encoding; this.expectedResult = expectedResult; treeCopy = HuffmanNode_DeepClone(tree); }
public static HuffmanNode HuffmanNode_DeepClone(HuffmanNode node) { return(node == null ? null : HuffmanNode_Create(node)); }
public bool Put(HuffmanNode node) => queue.Put(node, node.Frequency); // Dodaje węzeł Huffmana do kolejki