diff --git a/src/main/java/g3301_3400/s3345_smallest_divisible_digit_product_i/Solution.java b/src/main/java/g3301_3400/s3345_smallest_divisible_digit_product_i/Solution.java
new file mode 100644
index 000000000..a05f8ae9d
--- /dev/null
+++ b/src/main/java/g3301_3400/s3345_smallest_divisible_digit_product_i/Solution.java
@@ -0,0 +1,27 @@
+package g3301_3400.s3345_smallest_divisible_digit_product_i;
+
+// #Easy #Math #Enumeration #2024_11_13_Time_0_ms_(100.00%)_Space_41.2_MB_(29.77%)
+
+public class Solution {
+ public int smallestNumber(int n, int t) {
+ int num = -1;
+ int check = n;
+ while (num == -1) {
+ int product = findProduct(check);
+ if (product % t == 0) {
+ num = check;
+ }
+ check += 1;
+ }
+ return num;
+ }
+
+ private int findProduct(int check) {
+ int res = 1;
+ while (check > 0) {
+ res *= check % 10;
+ check = check / 10;
+ }
+ return res;
+ }
+}
diff --git a/src/main/java/g3301_3400/s3345_smallest_divisible_digit_product_i/readme.md b/src/main/java/g3301_3400/s3345_smallest_divisible_digit_product_i/readme.md
new file mode 100644
index 000000000..92ea91da9
--- /dev/null
+++ b/src/main/java/g3301_3400/s3345_smallest_divisible_digit_product_i/readme.md
@@ -0,0 +1,30 @@
+3345\. Smallest Divisible Digit Product I
+
+Easy
+
+You are given two integers `n` and `t`. Return the **smallest** number greater than or equal to `n` such that the **product of its digits** is divisible by `t`.
+
+**Example 1:**
+
+**Input:** n = 10, t = 2
+
+**Output:** 10
+
+**Explanation:**
+
+The digit product of 10 is 0, which is divisible by 2, making it the smallest number greater than or equal to 10 that satisfies the condition.
+
+**Example 2:**
+
+**Input:** n = 15, t = 3
+
+**Output:** 16
+
+**Explanation:**
+
+The digit product of 16 is 6, which is divisible by 3, making it the smallest number greater than or equal to 15 that satisfies the condition.
+
+**Constraints:**
+
+* `1 <= n <= 100`
+* `1 <= t <= 10`
\ No newline at end of file
diff --git a/src/main/java/g3301_3400/s3346_maximum_frequency_of_an_element_after_performing_operations_i/Solution.java b/src/main/java/g3301_3400/s3346_maximum_frequency_of_an_element_after_performing_operations_i/Solution.java
new file mode 100644
index 000000000..237eee454
--- /dev/null
+++ b/src/main/java/g3301_3400/s3346_maximum_frequency_of_an_element_after_performing_operations_i/Solution.java
@@ -0,0 +1,39 @@
+package g3301_3400.s3346_maximum_frequency_of_an_element_after_performing_operations_i;
+
+// #Medium #Array #Sorting #Binary_Search #Prefix_Sum #Sliding_Window
+// #2024_11_13_Time_7_ms_(96.84%)_Space_56.4_MB_(92.35%)
+
+public class Solution {
+ private int getMax(int[] nums) {
+ int max = nums[0];
+ for (int num : nums) {
+ max = Math.max(num, max);
+ }
+ return max;
+ }
+
+ public int maxFrequency(int[] nums, int k, int numOperations) {
+ int maxNum = getMax(nums);
+ int n = maxNum + k + 2;
+ int[] freq = new int[n];
+ for (int num : nums) {
+ freq[num]++;
+ }
+ int[] pref = new int[n];
+ pref[0] = freq[0];
+ for (int i = 1; i < n; i++) {
+ pref[i] = pref[i - 1] + freq[i];
+ }
+ int res = 0;
+ for (int i = 0; i < n; i++) {
+ int left = Math.max(0, i - k);
+ int right = Math.min(n - 1, i + k);
+ int tot = pref[right];
+ if (left > 0) {
+ tot -= pref[left - 1];
+ }
+ res = Math.max(res, freq[i] + Math.min(numOperations, tot - freq[i]));
+ }
+ return res;
+ }
+}
diff --git a/src/main/java/g3301_3400/s3346_maximum_frequency_of_an_element_after_performing_operations_i/readme.md b/src/main/java/g3301_3400/s3346_maximum_frequency_of_an_element_after_performing_operations_i/readme.md
new file mode 100644
index 000000000..d86c954eb
--- /dev/null
+++ b/src/main/java/g3301_3400/s3346_maximum_frequency_of_an_element_after_performing_operations_i/readme.md
@@ -0,0 +1,44 @@
+3346\. Maximum Frequency of an Element After Performing Operations I
+
+Medium
+
+You are given an integer array `nums` and two integers `k` and `numOperations`.
+
+You must perform an **operation** `numOperations` times on `nums`, where in each operation you:
+
+* Select an index `i` that was **not** selected in any previous operations.
+* Add an integer in the range `[-k, k]` to `nums[i]`.
+
+Return the **maximum** possible frequency of any element in `nums` after performing the **operations**.
+
+**Example 1:**
+
+**Input:** nums = [1,4,5], k = 1, numOperations = 2
+
+**Output:** 2
+
+**Explanation:**
+
+We can achieve a maximum frequency of two by:
+
+* Adding 0 to `nums[1]`. `nums` becomes `[1, 4, 5]`.
+* Adding -1 to `nums[2]`. `nums` becomes `[1, 4, 4]`.
+
+**Example 2:**
+
+**Input:** nums = [5,11,20,20], k = 5, numOperations = 1
+
+**Output:** 2
+
+**Explanation:**
+
+We can achieve a maximum frequency of two by:
+
+* Adding 0 to `nums[1]`.
+
+**Constraints:**
+
+* 1 <= nums.length <= 105
+* 1 <= nums[i] <= 105
+* 0 <= k <= 105
+* `0 <= numOperations <= nums.length`
\ No newline at end of file
diff --git a/src/main/java/g3301_3400/s3347_maximum_frequency_of_an_element_after_performing_operations_ii/Solution.java b/src/main/java/g3301_3400/s3347_maximum_frequency_of_an_element_after_performing_operations_ii/Solution.java
new file mode 100644
index 000000000..8b99ec754
--- /dev/null
+++ b/src/main/java/g3301_3400/s3347_maximum_frequency_of_an_element_after_performing_operations_ii/Solution.java
@@ -0,0 +1,41 @@
+package g3301_3400.s3347_maximum_frequency_of_an_element_after_performing_operations_ii;
+
+// #Hard #Array #Sorting #Binary_Search #Prefix_Sum #Sliding_Window
+// #2024_11_13_Time_30_ms_(98.88%)_Space_56.7_MB_(93.07%)
+
+import java.util.Arrays;
+
+public class Solution {
+ public int maxFrequency(int[] nums, int k, int numOperations) {
+ Arrays.sort(nums);
+ int n = nums.length;
+ int l = 0;
+ int r = 0;
+ int i = 0;
+ int j = 0;
+ int res = 0;
+ while (i < n) {
+ while (j < n && nums[j] == nums[i]) {
+ j++;
+ }
+ while (l < i && nums[i] - nums[l] > k) {
+ l++;
+ }
+ while (r < n && nums[r] - nums[i] <= k) {
+ r++;
+ }
+ res = Math.max(res, Math.min(i - l + r - j, numOperations) + j - i);
+ i = j;
+ }
+ i = 0;
+ j = 0;
+ while (i < n && j < n) {
+ while (j < n && j - i < numOperations && nums[j] - nums[i] <= k * 2) {
+ j++;
+ }
+ res = Math.max(res, j - i);
+ i++;
+ }
+ return res;
+ }
+}
diff --git a/src/main/java/g3301_3400/s3347_maximum_frequency_of_an_element_after_performing_operations_ii/readme.md b/src/main/java/g3301_3400/s3347_maximum_frequency_of_an_element_after_performing_operations_ii/readme.md
new file mode 100644
index 000000000..79914babd
--- /dev/null
+++ b/src/main/java/g3301_3400/s3347_maximum_frequency_of_an_element_after_performing_operations_ii/readme.md
@@ -0,0 +1,44 @@
+3347\. Maximum Frequency of an Element After Performing Operations II
+
+Hard
+
+You are given an integer array `nums` and two integers `k` and `numOperations`.
+
+You must perform an **operation** `numOperations` times on `nums`, where in each operation you:
+
+* Select an index `i` that was **not** selected in any previous operations.
+* Add an integer in the range `[-k, k]` to `nums[i]`.
+
+Return the **maximum** possible frequency of any element in `nums` after performing the **operations**.
+
+**Example 1:**
+
+**Input:** nums = [1,4,5], k = 1, numOperations = 2
+
+**Output:** 2
+
+**Explanation:**
+
+We can achieve a maximum frequency of two by:
+
+* Adding 0 to `nums[1]`, after which `nums` becomes `[1, 4, 5]`.
+* Adding -1 to `nums[2]`, after which `nums` becomes `[1, 4, 4]`.
+
+**Example 2:**
+
+**Input:** nums = [5,11,20,20], k = 5, numOperations = 1
+
+**Output:** 2
+
+**Explanation:**
+
+We can achieve a maximum frequency of two by:
+
+* Adding 0 to `nums[1]`.
+
+**Constraints:**
+
+* 1 <= nums.length <= 105
+* 1 <= nums[i] <= 109
+* 0 <= k <= 109
+* `0 <= numOperations <= nums.length`
\ No newline at end of file
diff --git a/src/main/java/g3301_3400/s3348_smallest_divisible_digit_product_ii/Solution.java b/src/main/java/g3301_3400/s3348_smallest_divisible_digit_product_ii/Solution.java
new file mode 100644
index 000000000..bf25e47ac
--- /dev/null
+++ b/src/main/java/g3301_3400/s3348_smallest_divisible_digit_product_ii/Solution.java
@@ -0,0 +1,75 @@
+package g3301_3400.s3348_smallest_divisible_digit_product_ii;
+
+// #Hard #String #Math #Greedy #Backtracking #Number_Theory
+// #2024_11_13_Time_21_ms_(100.00%)_Space_47_MB_(65.91%)
+
+public class Solution {
+ public String smallestNumber(String num, long t) {
+ long tmp = t;
+ for (int i = 9; i > 1; i--) {
+ while (tmp % i == 0) {
+ tmp /= i;
+ }
+ }
+ if (tmp > 1) {
+ return "-1";
+ }
+
+ char[] s = num.toCharArray();
+ int n = s.length;
+ long[] leftT = new long[n + 1];
+ leftT[0] = t;
+ int i0 = n - 1;
+ for (int i = 0; i < n; i++) {
+ if (s[i] == '0') {
+ i0 = i;
+ break;
+ }
+ leftT[i + 1] = leftT[i] / gcd(leftT[i], (long) s[i] - '0');
+ }
+ if (leftT[n] == 1) {
+ return num;
+ }
+ for (int i = i0; i >= 0; i--) {
+ while (++s[i] <= '9') {
+ long tt = leftT[i] / gcd(leftT[i], (long) s[i] - '0');
+ for (int j = n - 1; j > i; j--) {
+ if (tt == 1) {
+ s[j] = '1';
+ continue;
+ }
+ for (int k = 9; k > 1; k--) {
+ if (tt % k == 0) {
+ s[j] = (char) ('0' + k);
+ tt /= k;
+ break;
+ }
+ }
+ }
+ if (tt == 1) {
+ return new String(s);
+ }
+ }
+ }
+ StringBuilder ans = new StringBuilder();
+ for (int i = 9; i > 1; i--) {
+ while (t % i == 0) {
+ ans.append((char) ('0' + i));
+ t /= i;
+ }
+ }
+ while (ans.length() <= n) {
+ ans.append('1');
+ }
+ return ans.reverse().toString();
+ }
+
+ private long gcd(long a, long b) {
+ while (a != 0) {
+ long tmp = a;
+ a = b % a;
+ b = tmp;
+ }
+ return b;
+ }
+}
diff --git a/src/main/java/g3301_3400/s3348_smallest_divisible_digit_product_ii/readme.md b/src/main/java/g3301_3400/s3348_smallest_divisible_digit_product_ii/readme.md
new file mode 100644
index 000000000..4a24ceb5c
--- /dev/null
+++ b/src/main/java/g3301_3400/s3348_smallest_divisible_digit_product_ii/readme.md
@@ -0,0 +1,46 @@
+3348\. Smallest Divisible Digit Product II
+
+Hard
+
+You are given a string `num` which represents a **positive** integer, and an integer `t`.
+
+A number is called **zero-free** if _none_ of its digits are 0.
+
+Return a string representing the **smallest** **zero-free** number greater than or equal to `num` such that the **product of its digits** is divisible by `t`. If no such number exists, return `"-1"`.
+
+**Example 1:**
+
+**Input:** num = "1234", t = 256
+
+**Output:** "1488"
+
+**Explanation:**
+
+The smallest zero-free number that is greater than 1234 and has the product of its digits divisible by 256 is 1488, with the product of its digits equal to 256.
+
+**Example 2:**
+
+**Input:** num = "12355", t = 50
+
+**Output:** "12355"
+
+**Explanation:**
+
+12355 is already zero-free and has the product of its digits divisible by 50, with the product of its digits equal to 150.
+
+**Example 3:**
+
+**Input:** num = "11111", t = 26
+
+**Output:** "-1"
+
+**Explanation:**
+
+No number greater than 11111 has the product of its digits divisible by 26.
+
+**Constraints:**
+
+* 2 <= num.length <= 2 * 105
+* `num` consists only of digits in the range `['0', '9']`.
+* `num` does not contain leading zeros.
+* 1 <= t <= 1014
\ No newline at end of file
diff --git a/src/test/java/g3301_3400/s3345_smallest_divisible_digit_product_i/SolutionTest.java b/src/test/java/g3301_3400/s3345_smallest_divisible_digit_product_i/SolutionTest.java
new file mode 100644
index 000000000..693c1df60
--- /dev/null
+++ b/src/test/java/g3301_3400/s3345_smallest_divisible_digit_product_i/SolutionTest.java
@@ -0,0 +1,18 @@
+package g3301_3400.s3345_smallest_divisible_digit_product_i;
+
+import static org.hamcrest.CoreMatchers.equalTo;
+import static org.hamcrest.MatcherAssert.assertThat;
+
+import org.junit.jupiter.api.Test;
+
+class SolutionTest {
+ @Test
+ void smallestNumber() {
+ assertThat(new Solution().smallestNumber(10, 2), equalTo(10));
+ }
+
+ @Test
+ void smallestNumber2() {
+ assertThat(new Solution().smallestNumber(15, 3), equalTo(16));
+ }
+}
diff --git a/src/test/java/g3301_3400/s3346_maximum_frequency_of_an_element_after_performing_operations_i/SolutionTest.java b/src/test/java/g3301_3400/s3346_maximum_frequency_of_an_element_after_performing_operations_i/SolutionTest.java
new file mode 100644
index 000000000..2a71955bf
--- /dev/null
+++ b/src/test/java/g3301_3400/s3346_maximum_frequency_of_an_element_after_performing_operations_i/SolutionTest.java
@@ -0,0 +1,18 @@
+package g3301_3400.s3346_maximum_frequency_of_an_element_after_performing_operations_i;
+
+import static org.hamcrest.CoreMatchers.equalTo;
+import static org.hamcrest.MatcherAssert.assertThat;
+
+import org.junit.jupiter.api.Test;
+
+class SolutionTest {
+ @Test
+ void maxFrequency() {
+ assertThat(new Solution().maxFrequency(new int[] {1, 4, 5}, 1, 2), equalTo(2));
+ }
+
+ @Test
+ void maxFrequency2() {
+ assertThat(new Solution().maxFrequency(new int[] {5, 11, 20, 20}, 5, 1), equalTo(2));
+ }
+}
diff --git a/src/test/java/g3301_3400/s3347_maximum_frequency_of_an_element_after_performing_operations_ii/SolutionTest.java b/src/test/java/g3301_3400/s3347_maximum_frequency_of_an_element_after_performing_operations_ii/SolutionTest.java
new file mode 100644
index 000000000..17e4471b7
--- /dev/null
+++ b/src/test/java/g3301_3400/s3347_maximum_frequency_of_an_element_after_performing_operations_ii/SolutionTest.java
@@ -0,0 +1,18 @@
+package g3301_3400.s3347_maximum_frequency_of_an_element_after_performing_operations_ii;
+
+import static org.hamcrest.CoreMatchers.equalTo;
+import static org.hamcrest.MatcherAssert.assertThat;
+
+import org.junit.jupiter.api.Test;
+
+class SolutionTest {
+ @Test
+ void maxFrequency() {
+ assertThat(new Solution().maxFrequency(new int[] {1, 4, 5}, 1, 2), equalTo(2));
+ }
+
+ @Test
+ void maxFrequency2() {
+ assertThat(new Solution().maxFrequency(new int[] {5, 11, 20, 20}, 5, 1), equalTo(2));
+ }
+}
diff --git a/src/test/java/g3301_3400/s3348_smallest_divisible_digit_product_ii/SolutionTest.java b/src/test/java/g3301_3400/s3348_smallest_divisible_digit_product_ii/SolutionTest.java
new file mode 100644
index 000000000..741d32b7e
--- /dev/null
+++ b/src/test/java/g3301_3400/s3348_smallest_divisible_digit_product_ii/SolutionTest.java
@@ -0,0 +1,33 @@
+package g3301_3400.s3348_smallest_divisible_digit_product_ii;
+
+import static org.hamcrest.CoreMatchers.equalTo;
+import static org.hamcrest.MatcherAssert.assertThat;
+
+import org.junit.jupiter.api.Test;
+
+class SolutionTest {
+ @Test
+ void smallestNumber() {
+ assertThat(new Solution().smallestNumber("1234", 256L), equalTo("1488"));
+ }
+
+ @Test
+ void smallestNumber2() {
+ assertThat(new Solution().smallestNumber("12355", 50L), equalTo("12355"));
+ }
+
+ @Test
+ void smallestNumber3() {
+ assertThat(new Solution().smallestNumber("11111", 26L), equalTo("-1"));
+ }
+
+ @Test
+ void smallestNumber4() {
+ assertThat(new Solution().smallestNumber("10", 320L), equalTo("588"));
+ }
+
+ @Test
+ void smallestNumber5() {
+ assertThat(new Solution().smallestNumber("19", 2L), equalTo("21"));
+ }
+}