How do I strip empty lines from an InputStream? - java

What is the best way to strip empty lines from an InputStream in java?

A custom FilterReader can be used, preferably one that copes with different line endings (\n, \r, and \r\n) as well.
Usage:
StripEmptyLinesReader reader = new StripEmptyLinesReader(new InputStreamReader(origStream));
ReaderInputStream newStream = new ReaderInputStream(reader, someCharset);
Here's the class:
public class StripEmptyLinesReader extends FilterReader {
private char[] prevChars = new char[3];
public StripEmptyLinesReader(Reader reader) {
super(reader);
}
#Override
public int read(char[] buffer, int fromIndex, int length) throws IOException {
int numChars = 0;
while (numChars == 0) {
numChars = in.read(buffer, fromIndex, length);
if (numChars == -1) {
return -1;
}
int lastIndex = fromIndex;
for (int i = fromIndex; i < fromIndex + numChars; i++) {
int charsToSkip = numberOfNewlineCharactersToSkip(buffer[i]);
switch (charsToSkip) {
case 0:
buffer[lastIndex++] = buffer[i];
break;
case 2:
lastIndex--;
break;
}
prevChars[0] = buffer[i];
prevChars[1] = (i > 0) ? buffer[i - 1] : '\0';
prevChars[2] = (i > 1) ? buffer[i - 2] : '\0';
}
numChars = lastIndex - fromIndex;
}
return numChars;
}
private int numberOfNewlineCharactersToSkip(char currentChar) {
if ((currentChar == '\n' && prevChars[0] == '\n') || (currentChar == '\r' && prevChars[0] == '\r')) {
return 1;
}
if ((currentChar == '\n' && prevChars[0] == '\r' && prevChars[1] == '\n' && prevChars[2] == '\r')) {
return 2;
}
return 0;
}
#Override
public int read() throws IOException {
char[] buffer = new char[1];
int result = read(buffer, 0, 1);
return (result == -1) ? -1 : (int) buffer[0];
}
}

Related

more efficiently read int values from console

How can I read int values from console more efficiently (from memory) than this:
BufferedReader in ...
number = Integer.parseInt(in.readLine());
When I use readLine() and parse it to int, java create many String objects and сonsumes memory. I try to use Scanner and method nextInt() but this approach is also not that efficiently.
P.S I need read > 1000_000 values and I have memory limit.
EDIT Full code of task
import java.io.*;
public class Duplicate {
public static void main(String[] args) throws IOException {
int last = 0;
boolean b = false;
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
int n = Integer.parseInt(reader.readLine());
for (int i = 0; i < n; i++) {
int number =Integer.parseInt(reader.readLine());
if (number == 0 && !b) {
System.out.println(0);
b = true;
}
if (number == last) continue;
last = number;
System.out.print(last);
}
}
}
And Rewrite variant:
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.Reader;
public class Duplicate {
public static void main(String[] args) throws IOException {
int last = 0;
boolean b = false;
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
int nextInt = getNextInt(reader);
for (int i = 0; i < nextInt; i++) {
int number = getNextInt(reader);
if (number == 0 && !b) {
System.out.println(0);
b = true;
}
if (number == last) continue;
b = true;
last = number;
System.out.println(last);
}
}
static int getNextInt(Reader in) throws IOException {
int c;
boolean negative = false;
do {
c = in.read();
if (!Character.isDigit(c)) {
negative = c == '-';
}
} while (c != -1 && !Character.isDigit(c));
if (c == -1) return Integer.MIN_VALUE;
int num = Character.getNumericValue(c);
while ((c = in.read()) != -1 && Character.isDigit(c)) {
num = 10 * num + Character.getNumericValue(c);
}
return negative ? -num : num;
}
}
Both options do not pass from memory (((
EDIT2 I try profiling
int number = getRandom(); and start with 1000000
once again launched the same
and splash GC
You can read from in one char at a time, checking if it's a digit, and then accumulating it into a number. Something like:
int getNextInt(Reader in) throws IOException {
int c;
boolean negative = false;
do {
c = in.read();
if (!Character.isDigit(c)) { negative = c == '-' };
} while (c != -1 && !Character.isDigit(c));
if (c == -1) return Integer.MIN_VALUE; // Some sentinel to indicate nothing found.
int num = Character.getNumericValue(c);
while ((c = in.read()) != -1 && Character.isDigit(c)) {
num = 10 * num + Character.getNumericValue(c);
}
return negative ? -num : num;
}
Ideone demo
Of course, this is incredibly primitive parsing. But you could perhaps take this code as a basis and adapt it as required.
You can use this FastScanner class
static class FastScanner {
private BufferedReader reader = null;
private StringTokenizer tokenizer = null;
public FastScanner(InputStream in) {
reader = new BufferedReader(new InputStreamReader(in));
tokenizer = null;
}
public String next() {
if (tokenizer == null || !tokenizer.hasMoreTokens()) {
try {
tokenizer = new StringTokenizer(reader.readLine());
} catch (IOException e) {
throw new RuntimeException(e);
}
}
return tokenizer.nextToken();
}
public String nextLine() {
if (tokenizer == null || !tokenizer.hasMoreTokens()) {
try {
return reader.readLine();
} catch (IOException e) {
throw new RuntimeException(e);
}
}
return tokenizer.nextToken("\n");
}
public long nextLong() {
return Long.parseLong(next());
}
public int nextInt() {
return Integer.parseInt(next());
}
}
It is very commonly used on codeforces to read large input where Scanner class leads to TLE
This is originally authored by https://codeforces.com/profile/Petr
I use this InputReader on codeforces. Works pretty well for me on large input cases. You can extend this up to your use case. I came across this after getting TLE using Scanner and add functionalities if needed.
static class InputReader {
private final InputStream stream;
private final byte[] buf = new byte[1024];
private int curChar;
private int numChars;
public InputReader(InputStream stream) {
this.stream = stream;
}
private int read() {
try {
if (curChar >= numChars) {
curChar = 0;
numChars = stream.read(buf);
if (numChars <= 0)
return -1;
}
} catch (IOException e) {
throw new RuntimeException(e);
}
return buf[curChar++];
}
public int readInt() {
return (int) readLong();
}
public long readLong() {
int c = read();
while (isSpaceChar(c)) {
c = read();
if (c == -1) throw new RuntimeException();
}
boolean negative = false;
if (c == '-') {
negative = true;
c = read();
}
long res = 0;
do {
if (c < '0' || c > '9') throw new InputMismatchException();
res *= 10;
res += (c - '0');
c = read();
} while (!isSpaceChar(c));
return negative ? (-res) : (res);
}
public int[] readIntArray(int size) {
int[] arr = new int[size];
for (int i = 0; i < size; i++) arr[i] = readInt();
return arr;
}
private boolean isSpaceChar(int c) {
return c == ' ' || c == '\n' || c == '\r' || c == '\t' || c == -1;
}
}

Eclipse plugin: Folded Parts unfold everytime something is typed

What I have: I added a Reconciling Strategy to my Editor Plugin to determine the folding positions to enable code folding. It works very well, but if I execute my plugin, fold some code and type something, all the folded code parts unfold itselfs. I observed, that reconcile(IRegion partition) is the only method which gets called, and the offset of partition is always 0 and the length is always the length of the whole document. So there is always only one partition. How to change that?
The code for the Reconciling Strategy:
public class TFReconcilingStrategy implements IReconcilingStrategy {
IDocument doc = null;
TextEditorImpl editor = null;
ISourceViewer sourceViewer = null;
ModelState state = null;
public void reconcile(IRegion partition) {
updateEditor(partition.getOffset(),partition.getLength());
}
private void updateEditor(int offset, int length){
if (editor == null)
return;
createFoldingPositions(offset, length);
editor.redrawViewer();
}
//Determines where foldable positions are
private void createFoldingPositions(int offset, int length) {
final ArrayList<Position> positions = new ArrayList<Position>();
String content = editor.getDocument().get();
int line = 1, col = 1;
for(int i = 0; i < content.length(); i++){
if (content.charAt(i) == '\n'){
line++;
col = 1;
} else {
col++;
} //Curly Bracket Handling
if(content.charAt(i) == '{'){
int startOffset = 0;
try {
startOffset = doc.getLineOffset(line-1) + col -1;
} catch (BadLocationException e) {
e.printStackTrace();
}
int endOffset = getMatchingBracketPosition(line, col, i, content, '{', '}', 'z');
if (offset >= 0 && length > 0){
if (!(startOffset >= offset && endOffset <= (offset + length)))
continue;
}
if(endOffset != -1 && endOffset > 0){
Position pos = new Position(startOffset, (endOffset-startOffset));
positions.add(pos);
}
}//Edge Bracket Handling
if(content.charAt(i) == '[' && content.charAt(i+1) == '['){
int startOffset = 0;
try {
startOffset = doc.getLineOffset(line-1) + col -1;
} catch (BadLocationException e) {
e.printStackTrace();
}
int endOffset = getMatchingBracketPosition(line, col, i, content, '[', ']', 'z');
if (offset >= 0 && length > 0){
if (!(startOffset >= offset && endOffset <= (offset + length)))
continue;
}
if(endOffset != -1&& endOffset >0){ //if endoffset = -1 then the matching bracket is located in the same line
Position pos = new Position(startOffset, (endOffset-startOffset));
positions.add(pos);
}
}//Comment Handling
if(content.charAt(i) == '/' && content.charAt(i+1) == '*'){
int startOffset = 0;
try {
startOffset = doc.getLineOffset(line-1) + col -1;
} catch (BadLocationException e) {
e.printStackTrace();
}
int endOffset = getMatchingBracketPosition(line, col, i, content, '/', '*', '/');
if (offset >= 0 && length > 0){
if (!(startOffset >= offset && endOffset <= (offset + length)))
continue;
}
if(endOffset != -1 && endOffset >0){ //if endoffset = -1 then the matching bracket is located in the same line
Position pos = new Position(startOffset, (endOffset-startOffset));
positions.add(pos);
}
}
}
if (positions.size() > 0)
{
Display.getDefault().asyncExec(new Runnable() {
public void run() {
editor.updateFoldingStructure(positions);
editor.redrawViewer();
}
});
}
}
public void reconcile(DirtyRegion dirtyRegion, IRegion subRegion) {
updateEditor(dirtyRegion.getOffset(), dirtyRegion.getLength());
}
public void setDocument(IDocument document) {
doc = document;
updateEditor(-1,-1);
}
public void setEditor(TextEditorImpl editor){
this.editor = editor;
}
public void setSourceViewer (ISourceViewer viewer){
this.sourceViewer = viewer;
}
// param add is used, if the end of the foldable area is indicated by two chars
private int getMatchingBracketPosition(int line, int column, int position, String content, char openBracketType, char closedBracketType, char add){
int endOffset = 0;
int j = position;
boolean found = false;
int startLine = line;
int ignoredBrackets = 0;
while (j < content.length() && !found){
if (content.charAt(j) == '\n'){
line++;
column = 1;
} else {
column++;
}
if(content.charAt(j) == openBracketType){
ignoredBrackets++;
}
if (add == 'z'){
if (content.charAt(j) == closedBracketType){
ignoredBrackets--;
if(ignoredBrackets == 0){
found = true;
if(startLine != line){
try {
endOffset = doc.getLineOffset(line-1) + column -1;
} catch (BadLocationException e) {
e.printStackTrace();
}
}
else endOffset = -1;
}
}
} else {
if (content.charAt(j) == closedBracketType && content.charAt(j+1) == add){
ignoredBrackets--;
if(ignoredBrackets == 0){
found = true;
if(startLine != line){
try {
endOffset = doc.getLineOffset(line-1) + column -1;
} catch (BadLocationException e) {
e.printStackTrace();
}
}
else endOffset = -1;
}
}
}
j++;
}
return endOffset;
}
}
And the Code in my TextEditor Implementation:
public void redrawViewer(){
Display.getDefault().asyncExec(new Runnable() {
public void run() {
//refresh view
if ( getSourceViewer() != null)
getSourceViewer().getTextWidget().redraw();
}
});
}
and:
public void updateFoldingStructure(ArrayList positions){
Annotation[] annotations = new Annotation[positions.size()];
//this will hold the new annotations along
//with their corresponding positions
HashMap newAnnotations = new HashMap();
for(int i = 0; i < positions.size(); i++){
ProjectionAnnotation annotation = new ProjectionAnnotation();
newAnnotations.put(annotation,positions.get(i));
annotations[i]=annotation;
}
annotationModel.modifyAnnotations(oldAnnotations,newAnnotations,null);
oldAnnotations=annotations;
}
What I want: I want, that folded parts stay folded even though I type something. Hope someone can help me!

Time limit exceeded online judge

This is the problem :
Input
The first line of input will contain the number of test cases, T (1 ≤ T ≤ 50). Each of the following T
lines contains a positive integer N that is no more than 80 digits in length.
Output
The output of each test case will be a single line containing the smallest palindrome that is greater
than or equal to the input number.
Sample Input
2
42
321
Sample Output
44
323
I keep having time limit exceeded when i submit to the code to online judge ( 3 seconds limit)
class Main {
static String ReadLn (int maxLg)
{
byte lin[] = new byte [maxLg];
int lg = 0, car = -1;
String line = "";
try
{
while (lg < maxLg)
{
car = System.in.read();
if ((car < 0) || (car == '\n')) break;
lin [lg++] += car;
}
}
catch (IOException e)
{
return (null);
}
if ((car < 0) && (lg == 0)) return (null); // eof
return (new String (lin, 0, lg));
}
static boolean isPalandriome(String s){
String newString = "";
for(int i =s.length()-1;i >= 0; i--){
newString += s.charAt(i);
}
if(newString.equals(s))
return true;
else
return false;
}
public static void main(String[] args) {
BigInteger entredNumber;
String input;
input = Main.ReadLn(10);
int tests = Integer.parseInt(input);
List<BigInteger> numbers = new ArrayList<BigInteger>();
for (int i =0;i<tests;i++)
{
input = Main.ReadLn(100);
entredNumber = new BigInteger(input);
numbers.add(entredNumber);
}
for(int i=0;i<tests;i++){
BigInteger number = numbers.get(i);
while(!isPalandriome(String.valueOf(number))){
number = number.add(BigInteger.ONE);
}
System.out.println(number);
}
}
}
I can't find what takes too much time in my code.
At last coded Hope you find this helpful took 0.10 seconds
import java.io.IOException;
public class Main {
public static void main(String[] args) throws IOException {
CustomReader cr = new CustomReader(1000000);
int T = cr.nextInt(), fIndex, bIndex, fStartIndex, bStartIndex;
StringBuilder output = new StringBuilder();
byte[] input;
boolean isAppend1 = false;
for (int i = 0; i < T; i++) {
input = cr.nextInput();
fStartIndex = bStartIndex = cr.getCurrInputLength() / 2;
isAppend1 = false;
if (cr.getCurrInputLength() % 2 == 0) {
bStartIndex--;
}
fIndex = fStartIndex;
bIndex = bStartIndex;
while (input[bIndex] == input[fIndex]) {
if (bIndex - 1 < 0) {
break;
} else {
bIndex--;
fIndex++;
}
}
if (input[bIndex] > input[fIndex]) {
while (bIndex >= 0) {
input[fIndex++] = input[bIndex--];
}
} else {
if (input[bStartIndex] < 57) {
input[bStartIndex] = (byte) (input[bStartIndex] + 1);
} else {
bIndex = bStartIndex;
while (bIndex >= 0 && input[bIndex] == 57) {
input[bIndex] = 48;
bIndex--;
}
if (bIndex >= 0) {
input[bIndex] = (byte) (input[bIndex] + 1);
} else {
input[0] = 49;
if (fStartIndex != bStartIndex) {
input[fStartIndex] = 48;
bStartIndex = fStartIndex;
} else {
input[fStartIndex + 1] = 48;
bStartIndex = fStartIndex = fStartIndex + 1;
}
isAppend1 = true;
}
}
while (bStartIndex > -1) {
input[fStartIndex++] = input[bStartIndex--];
}
}
for (int j = 0; j < cr.getCurrInputLength(); j++) {
output.append((char) input[j]);
}
if (isAppend1) {
output.append("1");
}
output.append("\n");
}
System.out.print(output.toString());
// genInput();
}
private static class CustomReader {
private byte[] buffer;
private byte[] currInput = new byte[1000000];
private int currInputLength;
private int currIndex;
private int validBytesInBuffer;
CustomReader(int buffSize) {
buffer = new byte[buffSize];
}
public int nextInt() throws IOException {
int value;
byte b;
while (true) {
b = getNextByte();
if (b > 47 && b < 58) {
break;
}
}
value = b - 48;
while (true) {
b = getNextByte();
if (b > 47 && b < 58) {
value = (value * 10) + (b - 48);
} else {
break;
}
}
return value;
}
public byte[] nextInput() throws IOException {
byte b;
this.currInputLength = 0;
while (true) {
b = getNextByte();
if (b > 47 && b < 58) {
break;
}
}
currInput[currInputLength++] = b;
while (true) {
b = getNextByte();
if (b > 47 && b < 58) {
currInput[currInputLength++] = b;
} else {
break;
}
}
return this.currInput;
}
public int getCurrInputLength() {
return this.currInputLength;
}
private byte getNextByte() throws IOException {
if (currIndex == buffer.length || currIndex == validBytesInBuffer) {
validBytesInBuffer = System.in.read(buffer);
currIndex = 0;
}
return buffer[currIndex++];
}
}
public static void genInput() {
for (int i = 0; i < 100; i++) {
System.out.println((int) (Math.random() * 1000000000));
}
}
}

Why do we apply BFS/DFS in SPOJ(ALLIZWELL) ? Why would not simple brute force work?

Problem Link
By brute force I mean if I take 6 variables a,l,i,w,e,z for alphabet A,L,I,W,E,Z and count their number of occurrence apply condition as:
if(a<1||l<4||i<1||w<1||e<1||z<2)
{
System.out.println("NO");
}
else
System.out.println("YES");
What's wrong in that?
Here's my complete code and also I'm getting wrong answer.
import java.io.*;
public class Main {
public static void main(String asd[]) throws Exception {
Parser in = new Parser(System.in);
int t=in.nextInt();
while(t-->0)
{
int r=in.nextInt();
int c=in.nextInt();int a,l,i,z,w,e;
a=l=i=z=w=e=0;
for(int j=0;j<r;j++)
{
String s=in.next();
for(int k=0;k<s.length();k++)
{
char ch=s.charAt(k);
switch(ch)
{
case 'A':a++;break;
case 'L':l++;break;
case 'I':i++;break;
case 'Z':z++;break;
case 'W':w++;break;
case 'E':e++;break;
}
}
}
if(a<1||l<4||i<1||w<1||e<1||z<2)
{
System.out.println("NO");
}
else
System.out.println("YES");
}
}
}
// for inputting
class Parser {
final private int BUFFER_SIZE = 1 << 16;
private DataInputStream din;
private byte[] buffer;
private int bufferPointer, bytesRead;
public Parser(InputStream in) {
din = new DataInputStream(in);
buffer = new byte[BUFFER_SIZE];
bufferPointer = bytesRead = 0;
}
public long nextLong() throws Exception {
long ret = 0;
byte c = read();
while (c <= ' ') c = read();
boolean neg = c == '-';
if (neg) c = read();
do {
ret = ret * 10 + c - '0';
c = read();
} while (c > ' ');
if (neg) return -ret;
return ret;
}
//reads in the next string
public String next() throws Exception {
StringBuilder ret = new StringBuilder();
byte c = read();
while (c <= ' ') c = read();
do {
ret = ret.append((char) c);
c = read();
} while (c > ' ');
return ret.toString();
}
public int nextInt() throws Exception {
int ret = 0;
byte c = read();
while (c <= ' ') c = read();
boolean neg = c == '-';
if (neg) c = read();
do {
ret = ret * 10 + c - '0';
c = read();
} while (c > ' ');
if (neg) return -ret;
return ret;
}
private void fillBuffer() throws Exception {
bytesRead = din.read(buffer, bufferPointer = 0, BUFFER_SIZE);
if (bytesRead == -1) buffer[0] = -1;
}
private byte read() throws Exception {
if (bufferPointer == bytesRead) fillBuffer();
return buffer[bufferPointer++];
}
}
Just because the matrix contains enough letters doesn't mean there's a path that puts them all in the right order.
For a simple example, consider
AILLZZWELL
You need an L adjacent to the A, but there is none.
Have you ever played the game "Boggle?" It's basically the same concept.

UVa-784 Wrong Answer [closed]

Closed. This question is not reproducible or was caused by typos. It is not currently accepting answers.
This question was caused by a typo or a problem that can no longer be reproduced. While similar questions may be on-topic here, this one was resolved in a way less likely to help future readers.
Closed 8 years ago.
Improve this question
I am going crazy with this problem!
My solution is in Java - I have tried different inputs and haven't been able to reproduce the alleged wrong answer. Maybe someone here could possibly point to my solutions bottlenecks?
The verdict I am getting from UVa judge is "Wrong Answer".
// FOUND THE SOLUTION - I WAS PRINTING null chars at the end of some lines ('\u0000').
The problem is solved by adding if(maze[j][i] != '\u0000') before calling bufferedWriter.write(maze[j][i]
Thanks to everyone!
The intial code:
import java.io.*;
class Main {
public static final int MAX_NUMBER_OF_LINES = 31;
public static final int MAX_NUMBER_OF_CHARACTERS_PER_LINE = 81;
public static char[][] maze;
public static boolean[][] visitedLocations;
public static int numberOfMazes;
public static int numberOfLines;
public static int numberOfChars;
public static BufferedReader bufferedReader;
public static BufferedWriter bufferedWriter = new BufferedWriter(new OutputStreamWriter(System.out));
public static void main(String args[]) throws IOException {
readFromStandardInput();
bufferedWriter.flush();
}
public static void readFromStandardInput() throws IOException {
bufferedReader = new BufferedReader(new InputStreamReader(System.in));
String line;
numberOfMazes = Integer.parseInt(bufferedReader.readLine());
int lineCounter = 0;
while (numberOfMazes > 0) {
maze = new char[MAX_NUMBER_OF_CHARACTERS_PER_LINE][MAX_NUMBER_OF_LINES];
visitedLocations = new boolean[MAX_NUMBER_OF_CHARACTERS_PER_LINE][MAX_NUMBER_OF_LINES];
lineCounter = 0;
while ((line = bufferedReader.readLine()) != null) {
if (line.charAt(0) == '_') {
break;
} else {
constructArrayLineByLine(line, lineCounter);
}
lineCounter++;
}
numberOfLines = lineCounter;
solvePreviousMaze();
bufferedWriter.write(line);
numberOfMazes--;
if (numberOfMazes > 0) {
bufferedWriter.write("\n");
}
}
}
public static void solvePreviousMaze() throws IOException {
for (int i = 1; i < numberOfLines; i++) {
for (int j = 1; j < numberOfChars; j++) {
if (maze[j][i] == '*') {
floodTheMaze(i, j);
solutionToStandardOutput();
return;
}
}
}
}
public static void solutionToStandardOutput() throws IOException {
for (int i = 0; i < numberOfLines; i++) {
for (int j = 0; j < numberOfChars; j++) {
bufferedWriter.write(maze[j][i]);
}
bufferedWriter.write("\n");
}
}
public static void floodTheMaze(int i, int j) {
if (visitedLocations[j][i]) {
return;
} else {
visitedLocations[j][i] = true;
}
if (maze[j][i] == ' ' || maze[j][i] == '*') {
maze[j][i] = '#';
floodTheMaze(i, j - 1);
floodTheMaze(i - 1, j);
floodTheMaze(i + 1, j);
floodTheMaze(i, j + 1);
}
}
public static void constructArrayLineByLine(String line, int numberOfLine) {
numberOfChars = Math.max(numberOfChars, line.length());
for (int i = 0; i < line.length(); i++) {
maze[i][numberOfLine] = line.charAt(i);
}
}
}
One very clear bug in your solution is that you are printing extra 'space characters' in your solution which is probably not what the question asked. For example, in the first sample output, you are printing extra spaces in the lower 5 lines. You can solve this problem by using an arraylist of array to store the input and then output that arraylist.
Also, you should probably output a new line after every line of output. (You are not doing so for the last line of output.)
Here is a link to my accepted solution for this problem.
import java.io.*;
import java.math.*;
import java.util.*;
import java.lang.*;
public class Main{
public static InputStream inputStream = System.in;
public static OutputStream outputStream = System.out;
public static FastReader in = new FastReader(inputStream);
public static PrintWriter out = new PrintWriter(outputStream);
public static void main(String[] args)throws java.lang.Exception{
new Main().run();
out.close();
}
int N;
int M;
boolean[][] dfsNode;
StringTokenizer tk;
char[][] grid;
char[][] filled;
String[] sep;
void run()throws java.lang.Exception{
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
N = Integer.parseInt(br.readLine().trim());
sep = new String[N];
for(int i=0; i<N; i++){
ArrayList<char[]> al = new ArrayList<char[]>();
while(true){
String s = br.readLine();
if(s.contains("_")){
sep[i] = s;
break;
}
char[] arr = s.toCharArray();
al.add(arr);
}
grid = new char[al.size()][];
for(int j=0; j<al.size(); j++){
grid[j] = al.get(j);
}
// ArrayUtils.printGrid(grid);
int stari = -1;
int starj = -1;
for(int j=0; j<grid.length; j++){
for(int k=0; k<grid[j].length; k++){
if(grid[j][k] == '*'){
stari = j;
starj = k;
break;
}
}
}
dfsNode = new boolean[grid.length][];
filled = new char[grid.length][];
for(int j=0; j<grid.length; j++){
char[] arr = new char[grid[j].length];
for(int k=0; k<grid[j].length; k++){
arr[k] = grid[j][k];
}
filled[j] = arr;
dfsNode[j] = new boolean[grid[j].length];
}
fillColour(stari, starj);
for(int j=0; j<filled.length; j++){
for(int k=0; k<filled[j].length; k++){
if(filled[j][k] == '*'){
out.print(' ');
}else{
out.print(filled[j][k]);
}
}
out.println();
}
out.println(sep[i]);
}
}
void fillColour(int row, int col){
if(row<0 || row>=grid.length || col<0 || col>=grid[row].length){
return;
}
if(dfsNode[row][col]){
return;
}
// fill on border?
if(grid[row][col]!=' ' && grid[row][col]!='*'){
return;
}
filled[row][col] = '#';
dfsNode[row][col] = true;
fillColour(row-1, col);
fillColour(row+1, col);
fillColour(row, col-1);
fillColour(row, col+1);
}
}
class FastReader{
private boolean finished = false;
private InputStream stream;
private byte[] buf = new byte[1024];
private int curChar;
private int numChars;
private SpaceCharFilter filter;
public FastReader(InputStream stream){
this.stream = stream;
}
public int read(){
if (numChars == -1){
throw new InputMismatchException ();
}
if (curChar >= numChars){
curChar = 0;
try{
numChars = stream.read (buf);
} catch (IOException e){
throw new InputMismatchException ();
}
if (numChars <= 0){
return -1;
}
}
return buf[curChar++];
}
public int peek(){
if (numChars == -1){
return -1;
}
if (curChar >= numChars){
curChar = 0;
try{
numChars = stream.read (buf);
} catch (IOException e){
return -1;
}
if (numChars <= 0){
return -1;
}
}
return buf[curChar];
}
public int nextInt(){
int c = read ();
while (isSpaceChar (c))
c = read ();
int sgn = 1;
if (c == '-'){
sgn = -1;
c = read ();
}
int res = 0;
do{
if(c==','){
c = read();
}
if (c < '0' || c > '9'){
throw new InputMismatchException ();
}
res *= 10;
res += c - '0';
c = read ();
} while (!isSpaceChar (c));
return res * sgn;
}
public long nextLong(){
int c = read ();
while (isSpaceChar (c))
c = read ();
int sgn = 1;
if (c == '-'){
sgn = -1;
c = read ();
}
long res = 0;
do{
if (c < '0' || c > '9'){
throw new InputMismatchException ();
}
res *= 10;
res += c - '0';
c = read ();
} while (!isSpaceChar (c));
return res * sgn;
}
public String nextString(){
int c = read ();
while (isSpaceChar (c))
c = read ();
StringBuilder res = new StringBuilder ();
do{
res.appendCodePoint (c);
c = read ();
} while (!isSpaceChar (c));
return res.toString ();
}
public boolean isSpaceChar(int c){
if (filter != null){
return filter.isSpaceChar (c);
}
return isWhitespace (c);
}
public static boolean isWhitespace(int c){
return c == ' ' || c == '\n' || c == '\r' || c == '\t' || c == -1;
}
private String readLine0(){
StringBuilder buf = new StringBuilder ();
int c = read ();
while (c != '\n' && c != -1){
if (c != '\r'){
buf.appendCodePoint (c);
}
c = read ();
}
return buf.toString ();
}
public String nextLine(){
String s = readLine0 ();
while (s.trim ().length () == 0)
s = readLine0 ();
return s;
}
public String nextLine(boolean ignoreEmptyLines){
if (ignoreEmptyLines){
return nextLine ();
}else{
return readLine0 ();
}
}
public BigInteger nextBigInteger(){
try{
return new BigInteger (nextString ());
} catch (NumberFormatException e){
throw new InputMismatchException ();
}
}
public char nextCharacter(){
int c = read ();
while (isSpaceChar (c))
c = read ();
return (char) c;
}
public double nextDouble(){
int c = read ();
while (isSpaceChar (c))
c = read ();
int sgn = 1;
if (c == '-'){
sgn = -1;
c = read ();
}
double res = 0;
while (!isSpaceChar (c) && c != '.'){
if (c == 'e' || c == 'E'){
return res * Math.pow (10, nextInt ());
}
if (c < '0' || c > '9'){
throw new InputMismatchException ();
}
res *= 10;
res += c - '0';
c = read ();
}
if (c == '.'){
c = read ();
double m = 1;
while (!isSpaceChar (c)){
if (c == 'e' || c == 'E'){
return res * Math.pow (10, nextInt ());
}
if (c < '0' || c > '9'){
throw new InputMismatchException ();
}
m /= 10;
res += (c - '0') * m;
c = read ();
}
}
return res * sgn;
}
public boolean isExhausted(){
int value;
while (isSpaceChar (value = peek ()) && value != -1)
read ();
return value == -1;
}
public String next(){
return nextString ();
}
public SpaceCharFilter getFilter(){
return filter;
}
public void setFilter(SpaceCharFilter filter){
this.filter = filter;
}
public interface SpaceCharFilter{
public boolean isSpaceChar(int ch);
}
}

Categories

Resources