diff --git a/src/main/java/com/thealgorithms/datastructures/trees/BinaryTreeToString.java b/src/main/java/com/thealgorithms/datastructures/trees/BinaryTreeToString.java new file mode 100644 index 000000000000..2f9b3b489d56 --- /dev/null +++ b/src/main/java/com/thealgorithms/datastructures/trees/BinaryTreeToString.java @@ -0,0 +1,100 @@ +package com.thealgorithms.datastructures.trees; + +/** + * Leetcode 606: Construct String from Binary Tree: + * https://leetcode.com/problems/construct-string-from-binary-tree/ + * + * Utility class to convert a {@link BinaryTree} into its string representation. + *

+ * The conversion follows a preorder traversal pattern (root → left → right) + * and uses parentheses to denote the tree structure. + * Empty parentheses "()" are used to explicitly represent missing left children + * when a right child exists, ensuring the structure is unambiguous. + *

+ * + *

Rules:

+ * + * + *

Example:

+ * + *
+ *     Input tree:
+ *           1
+ *          / \
+ *         2   3
+ *          \
+ *           4
+ *
+ *     Output string:
+ *     "1(2()(4))(3)"
+ * 
+ * + *

+ * This implementation matches the logic from LeetCode problem 606: + * Construct String from Binary Tree. + *

+ * + * @author Muhammad Junaid + * @see BinaryTree + */ +public class BinaryTreeToString { + + /** String builder used to accumulate the string representation. */ + private StringBuilder sb; + + /** + * Converts a binary tree (given its root node) to its string representation. + * + * @param root the root node of the binary tree + * @return the string representation of the binary tree, or an empty string if + * the tree is null + */ + public String tree2str(BinaryTree.Node root) { + if (root == null) { + return ""; + } + + sb = new StringBuilder(); + dfs(root); + + // Remove the leading and trailing parentheses added by the root call + return sb.substring(1, sb.length() - 1); + } + + /** + * Performs a recursive depth-first traversal to build the string. + * Each recursive call appends the node value and its children (if any) + * enclosed in parentheses. + * + * @param node the current node being processed + */ + private void dfs(BinaryTree.Node node) { + if (node == null) { + return; + } + + sb.append("(").append(node.data); + + // Recursively build left and right subtrees + if (node.left != null) { + dfs(node.left); + } + + // Handle the special case: right child exists but left child is null + if (node.right != null && node.left == null) { + sb.append("()"); + dfs(node.right); + } else if (node.right != null) { + dfs(node.right); + } + + sb.append(")"); + } +} diff --git a/src/test/java/com/thealgorithms/datastructures/trees/BinaryTreeToStringTest.java b/src/test/java/com/thealgorithms/datastructures/trees/BinaryTreeToStringTest.java new file mode 100644 index 000000000000..2461fd74143d --- /dev/null +++ b/src/test/java/com/thealgorithms/datastructures/trees/BinaryTreeToStringTest.java @@ -0,0 +1,57 @@ +package com.thealgorithms.datastructures.trees; + +import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.Test; + +/** + * Tests for the BinaryTreeToString class. + */ +public class BinaryTreeToStringTest { + + @Test + public void testTreeToStringBasic() { + BinaryTree tree = new BinaryTree(); + tree.put(1); + tree.put(2); + tree.put(3); + tree.put(4); + + BinaryTreeToString converter = new BinaryTreeToString(); + String result = converter.tree2str(tree.getRoot()); + + // Output will depend on insertion logic of BinaryTree.put() + // which is BST-style, so result = "1()(2()(3()(4)))" + Assertions.assertEquals("1()(2()(3()(4)))", result); + } + + @Test + public void testSingleNodeTree() { + BinaryTree tree = new BinaryTree(); + tree.put(10); + + BinaryTreeToString converter = new BinaryTreeToString(); + String result = converter.tree2str(tree.getRoot()); + + Assertions.assertEquals("10", result); + } + + @Test + public void testComplexTreeStructure() { + BinaryTree.Node root = new BinaryTree.Node(10); + root.left = new BinaryTree.Node(5); + root.right = new BinaryTree.Node(20); + root.right.left = new BinaryTree.Node(15); + root.right.right = new BinaryTree.Node(25); + + BinaryTreeToString converter = new BinaryTreeToString(); + String result = converter.tree2str(root); + + Assertions.assertEquals("10(5)(20(15)(25))", result); + } + + @Test + public void testNullTree() { + BinaryTreeToString converter = new BinaryTreeToString(); + Assertions.assertEquals("", converter.tree2str(null)); + } +}