Java 这两种基于字符串的算法的复杂性是什么?
我编写了这两个算法来检查字符串中的重复字符(ABBC,AAAC)。第一种方法使用hashset数据结构,而第二种方法完全依赖于迭代 算法1Java 这两种基于字符串的算法的复杂性是什么?,java,performance,algorithm,big-o,time-complexity,Java,Performance,Algorithm,Big O,Time Complexity,我编写了这两个算法来检查字符串中的重复字符(ABBC,AAAC)。第一种方法使用hashset数据结构,而第二种方法完全依赖于迭代 算法1 String s = "abcdefghijklmnopqrstuvwxxyz"; public boolean isUnique(String s) { Set<Character> charSet = new HashSet<Character>(); for(int i=0; i<s.
String s = "abcdefghijklmnopqrstuvwxxyz";
public boolean isUnique(String s) {
Set<Character> charSet = new HashSet<Character>();
for(int i=0; i<s.length(); i++) {
if(charSet.contains(s.charAt(i))) {
return false;
}
charSet.add(s.charAt(i));
}
return true;
}
String s=“abcdefghijklmnopqrstuvxxyz”;
公共布尔值是唯一的(字符串s){
Set charSet=new HashSet();
对于(int i=0;i假设charAt方法在O(1)时间内运行,第一个算法是O(N),第二个是O(N^2)。对于所有输入,线性时间算法不应比二次算法快。在一定的N(可能是数百万)后,它将比二次算法快
例如:
void funcA(int n){
for (int i = 0; i < n; i++){
for (int j = 0; j < 10000; j++){
int k = i + j;
}
}
}
void funcB(int n){
for (int i = 0; i < n; i++){
for (int j = 0; j < n; j++){
int k = i + j;
}
}
}
void funcA(int n){
对于(int i=0;i
尽管funcA是线性的,funcB是二次的,但很容易看出,在n<10000的情况下,funcB比funcA快。在您的情况下,哈希集需要时间来计算哈希,因此对于特定大小的输入可能会慢一些。假设charAt方法在O(1)时间内运行,第一个算法是O(n),第二个算法是O(n^2)。对于所有输入,线性时间算法不应比二次算法快。在一定的N(可能是数百万)后,它将比二次算法快
例如:
void funcA(int n){
for (int i = 0; i < n; i++){
for (int j = 0; j < 10000; j++){
int k = i + j;
}
}
}
void funcB(int n){
for (int i = 0; i < n; i++){
for (int j = 0; j < n; j++){
int k = i + j;
}
}
}
void funcA(int n){
对于(int i=0;i
尽管funcA是线性的,funcB是二次的,但很容易看出,在n<10000的情况下,funcB将比funcA快。在您的情况下,哈希集需要时间来计算哈希,因此对于特定大小的输入可能会慢一些。当使用O()表示法时,您会忽略常量,这意味着O(n)==(10^10*n)。因此,当O(n^2)>O(n)渐近为真,对于较小的n值不一定为真。
在您的例子中,想象一下,调整哈希集后面的数组的大小可能比迭代输入更耗时。当使用O()表示法时,您忽略常量,这意味着O(n)==(10^10*n)。因此,虽然O(n^2)>O(n)渐近为真,但对于较小的n值,它不一定为真。
在您的情况下,想象一下,调整哈希集后面的数组的大小可能比迭代输入更耗时。例如,如果您将自己限制为英语字符(a-z),则测试数据会出现问题,如果字符串长度>26,则保证有重复的字符串。在特定示例中,您提供了字符串“abcdefghijklmnopqrstuvwxxyz”
被排序,重复的元素x
在末尾被找到。因此,迭代数组查找速度更快,因为在继续解析字符串时,在构建哈希集时会有开销
更好的测试方法是使用随机生成的大尺寸整数序列和大的最大值(例如Long.max\u值
下面是一个测试,它反驳了您关于数组搜索速度更快的断言。请运行几次并亲自查看。或者您可以从1000次运行中取平均值,以此类推:
public class FindDuplicatesTest {
public static final String s = generateRandomString(100000);
private static String generateRandomString(int numChars) {
Random random = new Random();
StringBuilder sb = new StringBuilder();
for (int i = 0; i < numChars; i++) {
int codePoint = random.nextInt(65536);
sb.append(Character.toChars(codePoint));
}
return sb.toString();
}
public boolean isUnique(String s) {
Set<Character> charSet = new HashSet<Character>();
for (int i = 0; i < s.length(); i++) {
if (charSet.contains(s.charAt(i))) {
return false;
}
charSet.add(s.charAt(i));
}
return true;
}
public boolean isUnique2(String s) {
for (int i = 0; i < s.length() - 1; i++) {
for (int j = i + 1; j < s.length(); j++) {
if (s.charAt(i) == s.charAt(j)) {
return false;
}
}
}
return true;
}
public static void main(String[] args) {
FindDuplicatesTest app = new FindDuplicatesTest();
long start = System.nanoTime();
boolean result = app.isUnique(s);
long stop = System.nanoTime();
System.out.println(result);
System.out.println("HashSet Search Time: " + (stop - start));
start = System.nanoTime();
result = app.isUnique2(s);
stop = System.nanoTime();
System.out.println(result);
System.out.println("Array Search Time: " + (stop - start));
}
}
公共类FindDuplicatesTest{
公共静态最终字符串s=GeneratorDomainString(100000);
专用静态字符串生成器动态字符串(int numChars){
随机=新随机();
StringBuilder sb=新的StringBuilder();
对于(int i=0;i
您的测试数据有问题,例如,如果您将自己限制为英语字符(a-z),则如果字符串长度>26,则保证有重复的字符串。在特定示例中,您提供了字符串“abcdefghijklmnopqrstuvxxyz”
被排序,重复的元素x
在末尾被找到。因此,迭代数组查找速度更快,因为在继续解析字符串时,在构建哈希集时会有开销
更好的测试方法是使用随机生成的大尺寸整数序列和大的最大值(例如Long.max\u值
下面是一个测试,它反驳了您关于数组搜索速度更快的断言。请运行几次并亲自查看。或者您可以从1000次运行中取平均值,以此类推:
public class FindDuplicatesTest {
public static final String s = generateRandomString(100000);
private static String generateRandomString(int numChars) {
Random random = new Random();
StringBuilder sb = new StringBuilder();
for (int i = 0; i < numChars; i++) {
int codePoint = random.nextInt(65536);
sb.append(Character.toChars(codePoint));
}
return sb.toString();
}
public boolean isUnique(String s) {
Set<Character> charSet = new HashSet<Character>();
for (int i = 0; i < s.length(); i++) {
if (charSet.contains(s.charAt(i))) {
return false;
}
charSet.add(s.charAt(i));
}
return true;
}
public boolean isUnique2(String s) {
for (int i = 0; i < s.length() - 1; i++) {
for (int j = i + 1; j < s.length(); j++) {
if (s.charAt(i) == s.charAt(j)) {
return false;
}
}
}
return true;
}
public static void main(String[] args) {
FindDuplicatesTest app = new FindDuplicatesTest();
long start = System.nanoTime();
boolean result = app.isUnique(s);
long stop = System.nanoTime();
System.out.println(result);
System.out.println("HashSet Search Time: " + (stop - start));
start = System.nanoTime();
result = app.isUnique2(s);
stop = System.nanoTime();
System.out.println(result);
System.out.println("Array Search Time: " + (stop - start));
}
}
公共类FindDuplicatesTest{
公共静态最终字符串s=GeneratorDomainString(100000);
专用静态字符串生成器动态字符串(int numChars){
随机=新兰德