I'm trying to solve https://leetcode.com/problems/longest-repeating-substring/
I want to use rolling hash to match strings.
However, my codes don't seem to work when I deal with modulo.
For a string with all same characters, the maximum length of repeating substring should be string.length - 1.
public class Main {
public static void main(String[] args) {
String str = "bbbbbbbbbbbbbbbbbbb";
System.out.println(str.length() - 1);
Solution s = new Solution();
System.out.println(s.longestRepeatingSubstring(str));
}
}
class Solution {
public int longestRepeatingSubstring(String S) {
HashSet<Long> h = new HashSet();
long mod = (long)1e7 + 7;
for(int i = S.length() - 1; i >0; i--){
h = new HashSet();
long c = 0;
int j = 0;
for(; j < i; j ++){
c = (c*26 % mod + S.charAt(j) - 'a')% mod;
}
h.add(c);
for(; j < S.length(); j++){
c -= (S.charAt(j - i ) - 'a') * Math.pow(26,i-1)% mod;
c = (c*26 % mod + S.charAt(j) - 'a')% mod;
if(h.contains(c)){
return i;
}
h.add(c);
}
}
return 0;
}
}
Playground for my codes: https://leetcode.com/playground/F4HkxbFQ
We cannot see your original link, we need a password.
The usage of modulo seems to be really complex.
Why not try something like this
class Scratch {
// "static void main" must be defined in a public class.
public static void main(String[] args) {
String str = "bbaaabbbbccbbbbbbzzzbbbbb";
System.out.println(str.length() - 1);
Solution s = new Solution();
System.out.println(s.longestRepeatingSubstring(str));
}
static class Solution {
public int longestRepeatingSubstring(String s) {
int max = -1;
int currentLength = 1;
char[] array = s.toCharArray();
for (int index = 1; index < array.length; index++) {
if (array[index - 1] == array[index]) {
currentLength++;
max = Math.max(max, currentLength);
} else {
currentLength = 1;
}
}
return max;
}
}
}
Related
I was trying to solve a problem based on value and weight. In the task i had to pick out the elements by their value and weight, and find the highest efficiency solution. I receive an answer, however i am having trouble outputting the elements that were used in order to get an answer.
I've tried creating a string in which i place the values, however it gives out an outofbounds error.
public static void main(String[] args) {
String z[] = new String[]{"a","b","c","d","e","f","g","h","l","m"};
int w[] = new int[]{10,2,4,6,8,1,7,11,4,5};
int c[] = new int[]{20,3,5,7,4,1,8,15,8,6};
int maxW = 50;
int n = c.length;
System.out.println("");
int a = Find(w,c,maxW,n,z);
System.out.println("max value is " + a);
}
static int max(int a, int b)
{
if(a>b)
{
return a;
}
return b;
}
public static int Find(int w[],int c[], int maxW,int n, String[]z)
{
int K[][] = new int[n + 1][maxW + 1];
String s = "";
// Build table K[][] in bottom up manner
for (int i = 0; i<= n; i++)
{
for(int j = 0; j<= maxW; j++)
{
if (i == 0 || j == 0)
{
K[i][j] = 0;
}
else if (w[i - 1]<= j)
{
K[i][j] = max(c[i - 1] + K[i - 1][j - w[i - 1]], K[i - 1][j]);
}
else
{
K[i][j] = K[i - 1][j];
}
}
}
return K[n][maxW];
}
}
i want to output the same index element in string z, as the index element that is used to find the efficiancy.
The ideal result would be something like this in a string:
a a a b c d e m
(Just an example)
Thank you in advance.
I need to find all the permutations for a given n(user input) without backtracking.
What i tried is:
import java.util.Scanner;
import java.util.Vector;
class Main {
private static int n;
private static Vector<Vector<Integer>> permutations = new Vector<>();
private static void get_n() {
Scanner user = new Scanner(System.in);
System.out.print("n = ");
n = user.nextInt();
}
private static void display(Vector<Vector<Integer>> permutations) {
for (int i = 0; i < factorial(n) - 1; ++i) {
for (int j = 0; j < n; ++j) {
System.out.print(permutations.elementAt(i).elementAt(j) + " ");
}
System.out.println();
}
}
private static int factorial(int n) {
int result = 1;
for (int i = 1; i <= n; ++i) {
result *= i;
}
return result;
}
private static int max(Vector<Integer> permutation) {
int max = permutation.elementAt(0);
for (int i = 1; i < permutation.size(); ++i)
if (permutation.elementAt(i) > max)
max = permutation.elementAt(i);
return max;
}
// CHECKS FOR ELEMENT COUNT AND 0 - (n-1) APPARITION
public static int validate_permutation(Vector<Integer> permutation) {
// GOOD NUMBER OF ELEMENTS
if (max(permutation) != permutation.size() - 1)
return 0;
// PROPER ELEMENTS APPEAR
for (int i = 0; i < permutation.size(); ++i)
if (!permutation.contains(i))
return 0;
return 1;
}
private static Vector<Integer> next_permutation(Vector<Integer> permutation) {
int i;
do {
i = 1;
// INCREMENT LAST ELEMENT
permutation.set(permutation.size() - i, permutation.elementAt(permutation.size() - i) + 1);
// IN A P(n-1) PERMUTATION FOUND n. "OVERFLOW"
while (permutation.elementAt(permutation.size() - i) == permutation.size()) {
// RESET CURRENT POSITION
permutation.set(permutation.size() - i, 0);
// INCREMENT THE NEXT ONE
++i;
permutation.set(permutation.size() - i, permutation.elementAt(permutation.size() - i) + 1);
}
} while (validate_permutation(permutation) == 0);
// OUTPUT
System.out.print("output of next_permutation:\t\t");
for (int j = 0; j < permutation.size(); ++j)
System.out.print(permutation.elementAt(j) + " ");
System.out.println();
return permutation;
}
private static Vector<Vector<Integer>> permutations_of(int n) {
Vector<Vector<Integer>> permutations = new Vector<>();
// INITIALIZE PERMUTATION SET WITH 0
for (int i = 0; i < factorial(n); ++i) {
permutations.addElement(new Vector<>());
for(int j = 0; j < n; ++j)
permutations.elementAt(i).addElement(0);
}
for (int i = 0; i < n; ++i)
permutations.elementAt(0).set(i, i);
for (int i = 1; i < factorial(n); ++i) {
// ADD THE NEXT PERMUTATION TO THE SET
permutations.setElementAt(next_permutation(permutations.elementAt(i - 1)), i);
System.out.print("values set by permutations_of:\t");
for (int j = 0; j < permutations.elementAt(i).size(); ++j)
System.out.print(permutations.elementAt(i).elementAt(j) + " ");
System.out.println("\n");
}
System.out.print("\nFinal output of permutations_of:\n\n");
display(permutations);
return permutations;
}
public static void main(String[] args) {
get_n();
permutations.addAll(permutations_of(n));
}
}
Now, the problem is obvious when running the code. next_permutation outputs the correct permutations when called, the values are set correctly to the corresponding the vector of permutations, but the end result is a mass copy of the last permutation, which leads me to believe that every time a new permutation is outputted by next_permutation and set into the permutations vector, somehow that permutation is also copied over all of the other permutations. And I can't figure out why for the life of me.
I tried both set, setElementAt, and an implementation where I don't initialize the permutations vector fist, but add the permutations as they are outputted by next_permutation with add() and I hit the exact same problem. Is there some weird way in which Java handles memory? Or what would be the cause of this?
Thank you in advance!
permutations.setElementAt(next_permutation(permutations.elementAt(i - 1)), i);
This is literally setting the vector at permutations(i) to be the same object as permutations[i-1]. Not the same value - the exact same object. I think this the source of your problems. You instead need to copy the values in the vector.
i'm trying to create a bubble sort but I there is something wrong with my code. The output is : 82345679. I would like it to be : 23456789.
package com.company;
public class Main {
public static void main(String[] args) {
// write your code here
int[] tab = {9,8,7,6,5,4,3,2};
int[] result = {9,8,7,6,5,4,3,2};
for (int i = 0; i < result.length; i++ ) {
if (i < result.length - 1 ) {
if (result[i] > result[i+1]) {
result = permute(result, i);
i = 0;
}
}
}
for (int i: result) {
System.out.print(i);
}
}
public static int[] permute (int[] tableau, int index) {
int temp;
temp = tableau[index];
tableau[index] = tableau[index+1];
tableau[index+1] = temp;
return tableau;
}
}
The issue is with the combination of i = 0 and i++ in the for loop. Whenever you go in the i = 0 branch, you end up restarting at 1 because of the i++. Resulting in always skipping the 8 after the first iteration where the 9 is moved to the end.
So, either restart at -1, or use a while loop and only increment in an else block. For example:
int i = 0;
while (i < result.length - 1) {
if (result[i] > result[i+1]) {
permute(result, i)
i = 0;
} else {
i++;
}
}
However, I would advise against the one-loop bubble sort, because the algorithm complexity is harder to see (it is still O(n^2), but with only one loop it can give the impression that it is O(n)).
You need two loops.
int swap;
for (int i = 0; i < ( result.length - 1 ); i++) {
for (int j = 0; j < result.length - 1; j++) {
if (result[j] > result[j+1]) {
swap = result[j];
result[j] = result[j+1];
result[j+1] = swap;
}
}
}
You need to have 2 loops in order to compare each number to the whole array..
example of bubble sorting
public static void bubbleSort(int[] numArray) {
int n = numArray.length;
int temp = 0;
for (int i = 0; i < n; i++) {
for (int j = 1; j < (n - i); j++) {
if (numArray[j - 1] > numArray[j]) {
temp = numArray[j - 1];
numArray[j - 1] = numArray[j];
numArray[j] = temp;
}
}
}
}
Refer to this question
Sorting an Array of int using BubbleSort
Can be done with ONE loop (although it is not the usual way to present the bubble sort):
public static void main (String args[]) {
int[] tab = {9,8,7,6,5,4,3,2};
int i=1; // let's do the bubble sort again
while (i < tab.length) {
// loop invariant : t[0] <= t[1] .... <= t[i-1]
if (tab[i-1] < tab[i]) { // bubble here
swap(tab, i-1, i);
if (i>1) {
i = i-1; // one step to the left....
}
} else {
i = i +1; // one step to the right
}
}
for (int x: tab) {
System.out.print(x);
}
}
static void swap(int[] t, int i, int j) {
int x = t[i];
t[i] = t[j];
t[j] = x;
}
I wrote a utility class for an nCr problem. It takes a generic array and returns all combinations (without repetition).
import java.util.ArrayList;
public class fooClass {
public static void main(String[] args) {
class Utils {
public int factorial(int n) {
int p = 1;
int i = 1;
while(i <= n) {
p *= i++;
}
return p;
}
public <T> ArrayList<T[]> combinations(T[] array, int r) {
int n = array.length;
int[] vec = new int[r];
int i, j, k, m, o;
for (i = 0; i < vec.length; i++) {
//int j = vec[i];
vec[i] = i;
}
ArrayList<T[]> result = new ArrayList<T[]>();
int total = factorial(n) / (factorial(r) * factorial(n - r));
for (i = 0; i < total; i++) {
T[] combination = (T[])new Object[r];
for (k = 0; k < r; k++) {
combination[k] = array[vec[k]];
}
result.add(combination);
j = r - 1;
if (vec[j] + 1 < n) {
vec[j]++;
} else {
o = j;
while (j-- >= 0) {
if (vec[j] + 1 < n - r - (j + 1)) {
vec[j]++;
m = j + 1;
while (m++ <= o) {
vec[m] = vec[m-1] + 1;
}
break;
} //if end
} //while end
} //if-else end
}
return result;
}
};
Utils utils = new Utils();
String test = "abcde";
ArrayList<char[]> combinations = utils.combinations(test.toCharArray(), 3);
}
}
Now the issue is on the line there I am calling it; the compiler complains when I pass a char[].
The method combinations(T[], int) in the type Utils is not applicable for the arguments (char[], int)
What is the correct way to resolve this?
I think this is because char is a primitive type and T represents an object. If you use Character[] instead of char[], it should work just fine.
char[] chars = test.toCharArray();
Character[] arg = new Character[chars.length];
for (int i = 0; i < chars.length; i++)
arg[i] = chars[i];
ArrayList<Character[]> combinations = utils.combinations(arg, 3);
This copies all of the characters from the char array into the Character array and then passes it to the method.
I am trying to make an int method that converts a binary number into a base 10 number. I think my loop is structured correctly, but I cant figure out how to relate index position to an exponent. Basically if there is a '1' in the string, i want to return it as 2 to the power of whatever the index position of that char is. Also, this would require me to inverse the index (so that the 0 position is the rightmost char of the string. Here is what I have so far:
public static int BinaryToNumber(String numberInput)
{
int len = numberInput.length();
for(int i=len-1; i<len; i--)
{
if(i == '1');
{
return n;
}
}
return 0;
}
Thank you in advance!
I would prefer the Java built-in routines when possible - as I said in my comment Integer.parseInt(numberInput, 2);. By convention, Java method names begin with a lower case letter. Finally, you can fix your code (and I added a small test harness) with something like,
public static int binaryToNumber(String numberInput) {
if (numberInput == null) {
return 0;
}
int ret = 0;
char[] ni = numberInput.trim().toCharArray();
for (int i = 0; i < ni.length; i++) {
if (ni[i] == '1') {
// This is 2 ^ (n) where (n) is based on the position from the right.
ret += 1 << ni.length - i - 1;
}
}
return ret;
}
public static void main(String[] args) {
for (int i = 0; i < 10; i++) {
String t = Integer.toBinaryString(i);
System.out.printf("%s = %d%n", t, binaryToNumber(t));
}
}
this is my implementation for the problem
public static void main(String[] args) {
String str = "100101";
System.out.println(toDecimal(str));
}
private static int toDecimal(String binary) {
int result = 0;
for(int i = 0; i < binary.length(); i++) {
int a = (int) binary.charAt(i) - 48;
double secondPart = 1 << (binary.length()-1) - i;
result += a * secondPart;
}
return result;
}
I hope that helps
Salam