Home > Software design >  Kattis Issue, Texture Analysis. Java
Kattis Issue, Texture Analysis. Java

Time:09-18

I'm having issues with debugging the texture analysis on Kattis. I'm able to finish every test case i can imagine but yet the last test case fails. Does anyone have any idea what might be causing the last test case to fail?

Link to the kattis problem

public static void main(String[] args) throws Exception {
    BufferedReader sc = new BufferedReader(new InputStreamReader(System.in));
    BufferedWriter dc = new BufferedWriter(new OutputStreamWriter(System.out));

    int numOfLines = 1;

    for (;;) {
        String inputLine = sc.readLine();
        if (inputLine.equals("END"))
            break;
        else if (!inputLine.contains(".")) {
            dc.write(numOfLines     " EVEN\n");
        } else {
            //Next two lines creates an array out of the characters in a single line
            String[] tempArray = inputLine.split("");
            ArrayList<String> charArray = new ArrayList<String>(Arrays.asList(tempArray));
            //Next block of code finds all elements where an asterix has been found and puts them in the allIndexes array
            //If the code is even, the elements will for example be on 0, 2, 4, 6
            //If the code is uneven, the elements will for example be on 0, 1, 5, 8
            String str = "*";
            List<Integer> allIndexes =
                    IntStream.range(0, charArray.size()).boxed()
                            .filter(j -> charArray.get(j).equals(str))
                            .collect(Collectors.toList());

            ArrayList<Integer> duplicateList = new ArrayList<>();
            //For-loop, is used to normalize numbers
            //An even array of 0,2,4,6 turns into 2,2,2,2
            //An uneven array of 0,2,6,8 turns into 2,4,2,2
            //This means we can easily see where the uneven number is
            for (int j = 0; j < allIndexes.size(); j  ) {
                if(j < allIndexes.size() - 1)
                    duplicateList.add(allIndexes.get(j   1) - allIndexes.get(j));
            }
            Boolean isArrayUneven = false;
            //Here we check for uneven numbers in the array
            //If one is found then isArrayUneven turns true.
            for (int i = 1; i < duplicateList.size();i  ) {
                if (duplicateList.get(0) != duplicateList.get(i)) {
                    isArrayUneven = true;
                }
            }
            if (isArrayUneven ==true ) {
                dc.write(numOfLines     " NOT EVEN"   "\n");
            }
            else{
                dc.write(numOfLines     " EVEN"   "\n");
            }
        }
    }
    dc.close();
    sc.close();
}

CodePudding user response:

Although the solution seems a bit overengineered to me, I coded a working solution which was accepted by Kattis, then compared it against yours with a script on a variety of tests and couldn't find any differences. There's a slight chance it's a Java version behavior or platform issue of some sort, but I can't imagine what. Here's my solution and testing script in case it helps:

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;

public class TextureAnalysis {
    public static void main(String[] args) throws java.io.IOException {
        var sc = new BufferedReader(new InputStreamReader(System.in));
        var dc = new BufferedWriter(new OutputStreamWriter(System.out));

        for (int i = 1;; i  ) {
            String s = sc.readLine();
    
            if (s.equals("END")) {
                break;
            }

            var a = s.split("\\*", -1);
            boolean allSameLength = true;

            for (int j = 2; j < a.length - 1; j  ) {
                if (a[j].length() != a[1].length()) {
                    allSameLength = false;
                    break;
                }
            }

            dc.write(i   (allSameLength ? " EVEN\n" : " NOT EVEN\n"));
        }

        dc.close();
        sc.close();
    }
}

Testing script:

import random
import sys
from subprocess import Popen, PIPE


def start(cmd):
    return Popen(cmd, stdin=PIPE, stdout=PIPE, stderr=PIPE)


def read(process):
    return process.stdout.read().decode("utf-8")


def write(process, s):
    process.stdin.write(f"{s}\n".encode("utf-8"))
    process.stdin.flush()


def terminate(process):
    process.stdin.close()
    process.terminate()
    process.wait(timeout=0.2)


def main():
    # even tests
    for i in range(100):
        good = start(["java", "TextureAnalysis"])
        bad = start(["java", "TextureAnalysisBad"])

        for j in range(100):
            chunk = "*".join(["." * i for _ in range(j)])
            test = "*"   chunk   "*"
            write(good, test)
            write(bad, test)

        write(good, "END")
        write(bad, "END")
        g = read(good)
        b = read(bad)

        if g != b:
            print("FAIL:", test)
            sys.exit(0)

    # random tests, mostly uneven
    for _ in range(1000000):
        good = start(["java", "TextureAnalysis"])
        bad = start(["java", "TextureAnalysisBad"])
        
        for j in range(100):
            chunk = "".join(
                [random.choice(".*") for _ in range(random.randint(10, 150))]
            )
            test = "*"   chunk   "*"
            write(good, test)
            write(bad, test)
        
        write(good, "END")
        write(bad, "END")
        g = read(good)
        b = read(bad)
        
        if g != b:
            print("FAIL:", test)
            sys.exit(0)


if __name__ == "__main__":
    main()

(credit to this post for subprocess code)

CodePudding user response:

Fix your arrays to take more elements

  • Related