-1
            import java.util.Scanner;
            class same
          {static void anagram(String s1,String s2)
{int p=0;
    char[] c1=s1.toCharArray();
    char[] c2=s2.toCharArray();
    if(s1.length()!=s2.length())
    {
        System.out.println("not anagram");
        System.exit(0);
    }
    for(int i=0;i<s1.length();i++)
    {
        for(int j=0;j<s1.length();j++)
        {
            if(c1[i]==c2[j])
                c2[j]='\\';
        }
    }


        while
        ( p<s2.length()&&c2[p]=='\\')
        {
            p=p+1;

        }


        if(p==s2.length())
            System.out.println("anagram");
        else

    System.out.println("non anagram");


}
public static void main(String[] args)
{Scanner input=new Scanner(System.in);
System.out.println("enter the two strings");

String s1=input.next();
String s2=input.next();


    anagram(s1,s2);
}}

This code checks whether the two strings are anagram or not.

Can you tell me the performance of this code? Is it lengthy(time complexity) or not?

Or should I improve quality of my code? And thanx for previous suggestion.It is my first post and i am new to java.

anuj
  • 31
  • 2
  • 4
    I'd worry about the correctness of the code first, before thinking about performance: this code pretty obviously doesn't work for anything except 4-character strings which don't already contain backslashes; and even then it isn't doesn't work. – Andy Turner Oct 30 '15 at 12:38
  • 2
    Wouldn´t this make `APPLE` and `LAAPE` an anagram? I think you should just count the amount each `char` appears in each string and compare both arrays, or `Map` – SomeJavaGuy Oct 30 '15 at 12:40
  • Why not test the performance yourself? Performance may vary by the hardware it is running on. – pete the pagan-gerbil Oct 30 '15 at 12:42
  • 2
    Why oh why do novices always jump towards performance as if that is a prime concern. This code is terribly unreadable, yet apparently that was no concern at all. – Gimby Oct 30 '15 at 12:46
  • 2
    Your algorithm has n^2 + n operations, so it is O(n^2) (although god knows why you have n fixed at 4). You can produce an O(n) algorithm by counting the times each character appears on each string, as suggested above. Of course, since nothing is free, your memory complexity will then increase fromn O(1) to O(n). – Eduardo Javier Huerta Yero Oct 30 '15 at 12:46
  • Try to understand the essence of the problem first - what is the characteristic property of an anagram ? – collapsar Oct 30 '15 at 12:53
  • 1
    @collapsar could you eleborate which part of my comment you are refering to? because i have problems to understand what you are trying to say. – SomeJavaGuy Oct 30 '15 at 12:55
  • @EduardoJavierHuertaYero Your comment should really be an answer as it answers "Can you tell me the performance of this code?". – Michael Lloyd Lee mlk Oct 30 '15 at 13:04

2 Answers2

0

Since you don't iterate over any dynamic length but all iterations are with a limit of 4, the complexity of the code is ... O(1).

Dominik Sandjaja
  • 6,326
  • 6
  • 52
  • 77
0

I've tried two ways, A is sorting the characters of both strings alphabetically and comparing the results, B is counting every character in both strings and comparing the counts. I'd prefer A over B regarding readability.

public boolean isAnagramA(String a, String b) {
    if (a.length() != b.length()) {
        return false;
    }
    char[] aAsArray = a.toUpperCase().toCharArray();
    char[] bAsArray = b.toUpperCase().toCharArray();
    Arrays.sort(aAsArray);
    Arrays.sort(bAsArray);
    return Arrays.equals(aAsArray, bAsArray);
}

public int numberOf(char needle, char[] haystack) {
    int count = 0;
    for (int i = 0; i < haystack.length; i++) {
        if (haystack[i] == needle) {
            count++;
        }
    }
    return count;
}

public boolean isAnagramB(String a, String b) {
    if (a.length() != b.length()) {
        return false;
    }
    char[] aAsArray = a.toUpperCase().toCharArray();
    char[] bAsArray = b.toUpperCase().toCharArray();
    for (int i = 0; i < aAsArray.length; i++) {
        if (numberOf(aAsArray[i], aAsArray) != numberOf(aAsArray[i], bAsArray)) {
            return false;
        }
    }
    return true;
}

public void run() {
    {
        long start = System.nanoTime();
        System.out.println(isAnagramA("OTTO", "TOT"));
        System.out.println(isAnagramA("OTTO", "TOTO"));
        System.out.println(isAnagramA("LOTTO", "TOLLO"));
        System.out.println(isAnagramA("yarm", "army"));
        System.out.println(isAnagramA("Yarm", "Army"));
        System.out.println(isAnagramA("SMAISMRMILMEPOETALEVMIBVNENVGTTAVIRAS",
                "AltissimvmPlanetamTergeminvmObservavi"));
        System.out.println((System.nanoTime() - start) + " ns for 6 x A");
    }
    {
        long start = System.nanoTime();
        System.out.println(isAnagramB("OTTO", "TOT"));
        System.out.println(isAnagramB("OTTO", "TOTO"));
        System.out.println(isAnagramB("LOTTO", "TOLLO"));
        System.out.println(isAnagramB("yarm", "army"));
        System.out.println(isAnagramB("Yarm", "Army"));
        System.out.println(isAnagramB("SMAISMRMILMEPOETALEVMIBVNENVGTTAVIRAS",
                "AltissimvmPlanetamTergeminvmObservavi"));
        System.out.println((System.nanoTime() - start) + " ns for 6 x B");
    }
    {
        long start = System.currentTimeMillis();
        for (int i = 0; i < 1000000; i++) {
            isAnagramA("SMAISMRMILMEPOETALEVMIBVNENVGTTAVIRAS", "AltissimvmPlanetamTergeminvmObservavi");
        }
        System.out.println((System.currentTimeMillis() - start) + " ms for 1000000 x A");
    }
    {
        long start = System.currentTimeMillis();
        for (int i = 0; i < 1000000; i++) {
            isAnagramB("SMAISMRMILMEPOETALEVMIBVNENVGTTAVIRAS", "AltissimvmPlanetamTergeminvmObservavi");
        }
        System.out.println((System.currentTimeMillis() - start) + " ms for 1000000 x B");
    }
}

Method run() is used to test whether it works (not JUnit, just output) and which ways is faster, this is the output:

false
true
false
true
true
true
579384 ns for 6 x A
false
true
false
true
true
true
252453 ns for 6 x B
1310 ms for 1000000 x A
1333 ms for 1000000 x B

At first A seems to be two times slower but looping 1000000 times over checking Galileo Galilei's anagram shows almost no difference in performance (hopefully it's not due to compiler optimization).

I do agree with other commenters about caring for correctness and readability first and research optimizations only if and where there is a real need for it.

yasd
  • 916
  • 7
  • 21