How to read BufferedReader faster - java

I want to optimize this code:
InputStream is = rp.getEntity().getContent();
BufferedReader reader = new BufferedReader(new InputStreamReader(is));
String text = "";
String aux = "";
while ((aux = reader.readLine()) != null) {
text += aux;
}
The thing is that i don't know how to read the content of the bufferedreader and copy it in a String faster than what I have above.
I need to spend as little time as possible.
Thank you

Using string concatenation in a loop is the classic performance killer (because Strings are immutable, the entire, increasingly large String is copied for each concatenation). Do this instead:
StringBuilder builder = new StringBuilder();
String aux = "";
while ((aux = reader.readLine()) != null) {
builder.append(aux);
}
String text = builder.toString();

You can try Apache IOUtils.toString. This is what they do:
StringWriter sw = new StringWriter();
char[] buffer = new char[1024 * 4];
int n = 0;
while (-1 != (n = input.read(buffer))) {
sw.write(buffer, 0, n);
}
String text = sw.toString();

When BufferedReader reads from Socket, it is necessary to add bufferedReader.ready():
BufferedReader br = new BufferedReader(new InputStreamReader(socket.getInputStream()));
StringBuilder sb= new StringBuilder();
String line = "";
while (br.ready() && (line = br.readLine()) != null) {
sb.append(line + "\r\n");
}
String result = sb.toString();

One line solution:
String result = reader.lines().collect(joining(lineSeparator()));
Imports:
import java.io.*;
import static java.lang.System.lineSeparator;
import static java.util.stream.Collectors.joining;

I wrote a simple function to do this using StringBuilder and While loop with catching IOException inside.
public String getString(BufferedReader bufferedReader) {
StringBuilder stringBuilder = new StringBuilder();
String line = null;
do {
try {
if ((line = bufferedReader.readLine()) != null) {
stringBuilder.append(line).append(System.lineSeparator());
}
} catch (IOException e) {
e.printStackTrace();
}
} while (line != null);
return stringBuilder.toString();
}

You can use StringBuffer
while ((aux = reader.readLine()) != null) {
stringBuffer.append(aux);
}

Related

How to search and remove some values from xml java

I have an xml abc.xml
<soapenv:Envelope>
<soapenv:Header/>
<soapenv:Body>
<mes:SomeRq>
<RqID>?</RqID>
<MsgRqHdr>
....
</mes:SomeRq>
</soapenv:Body>
</soapenv:Envelope>
Is there a way i can search mes:, from this xml and replace it with ins:
Thanks in advance.
public static void findreplcae(String strFilePath) throws IOException {
String currentString = "mes:";
String changedString = "ins:";
BufferedReader reader = new BufferedReader(new FileReader(strFilePath));
StringBuffer currentLine = new StringBuffer();
String currentLineIn;
while ((currentLineIn = reader.readLine()) != null) {
System.out.println(currentLineIn);
boolean bool = false;
String trimmedLine = currentLineIn.trim();
System.out.println(trimmedLine);
if (trimmedLine.contains(currentString)) {
trimmedLine.replace(currentString, changedString);
bool = true;
if (bool != true) {
currentLine = currentLine.append(currentLineIn + System.getProperty("line.separator"));
}
}
reader.close();
BufferedWriter writer = new BufferedWriter(new FileWriter(strFilePath));
writer.write(currentLine.toString());
writer.close();
}
}
It's not good idea to parse it as a text file. DocumentBuilder.parse to parse the file, call getDocumentElement() and check for getPrefix. If it matches, replace with setPrefix(). Note you have to register prefix if not yet done already.
Check this page for tutorial.
Some issues:
trimmedLine.replace(currentString, changedString);, the result is returned, so you have to store it somewhere. See here
What is this supposed to do?
bool = true;
if (bool != true) {
currentLine = currentLine.append(currentLineIn + System.getProperty("line.separator"));
}
Don't close the reader while reading in a loop.
If you want to overwrite the original file, this should do (although I am not sure, if you really want to trim the lines):
String currentString = "mes:";
String changedString = "ins:";
try {
BufferedReader reader = new BufferedReader(new FileReader(strFilePath));
StringBuffer newContents = new StringBuffer();
String currentLineIn = null;
while ((currentLineIn = reader.readLine()) != null) {
String trimmedLine = currentLineIn.trim();
if (trimmedLine.contains(currentString)) {
newContents.append(trimmedLine.replace(currentString, changedString));
}
else {
newContents.append(trimmedLine);
}
newContents.append(System.getProperty("line.separator"));
}
reader.close();
BufferedWriter writer = new BufferedWriter(new FileWriter(strFilePath));
writer.write(newContents.toString());
writer.close();
} catch (IOException e) {
// TODO handle it
}

How to append multiple text in text file

I want the results from 'name' and 'code' to be inserted into log.txt file, but if I run this program only the name results gets inserted into .txt file, I cannot see code results appending under name. If I do System.outprintln(name) & System.outprintln(code) I get results printed in console but its not being inserted in a file.Can someone tell me what am I doing wrong?
Scanner sc = new Scanner(file, "UTF-8");
BufferedReader br = new BufferedReader(new FileReader(file));
PrintWriter out = new PrintWriter(new FileWriter("log.txt", true));
while ((line = br.readLine()) != null) {
if (line.contains("text1")) {
String[] splits = line.split("=");
String name = splits[2];
for (int i = 0; i < name.length(); i++) {
out.println(name);
}
}
if (line.contains("text2")) {
String[] splits = line.split("=");
String code = splits[2];
for (int i = 0; i < code.length(); i++) {
out.println(code);
}
}
out.close()
}
File looks like:
Name=111111111
Code=333,5555
Category-Warranty
Name=2222222
Code=111,22
Category-Warranty
Have a look at this code. Does that work for you?
final String NAME = "name";
final String CODE = "code";
BufferedReader br = new BufferedReader(new FileReader(file));
PrintWriter out = new PrintWriter(new FileWriter("log.txt", true));
while ((line = br.readLine()) != null) {
String[] splits = line.split("=");
String key = splits[0];
String value = splits[1];
if (key.equals(NAME) || key.equals(CODE)) {
out.println(value);
}
}
out.close();
You have a couple of problems in your code:
you never actually assign the variables name and code.
you close() your PrintWriter inside the while-loop, that means you will have a problem if you read more than one line.
I don't see why this wouldn't work, without seeing more of what you are doing:
BufferedReader br = new BufferedReader(new FileReader(file));
PrintWriter out = new PrintWriter(new FileWriter("log.txt", true));
while ((line = br.readLine()) != null) {
if (line.contains("=")) {
if (line.contains("text1")) {
String[] splits = line.split("=");
if (splits.length >= 2) {
out.println(splits[1]);
}
}
if (line.contains("text2")) {
String[] splits = line.split("=");
if (splits.length >= 2) {
out.println(splits[1]);
}
}
}
}
out.flush();
out.close();
Make sure the second if condition is satisfied i.e. the line String contains "text2".

BufferedReader to skip first line

I am using the following bufferedreader to read the lines of a file,
BufferedReader reader = new BufferedReader(new FileReader(somepath));
while ((line1 = reader.readLine()) != null)
{
//some code
}
Now, I want to skip reading the first line of the file and I don't want to use a counter line int lineno to keep a count of the lines.
How to do this?
You can try this
BufferedReader reader = new BufferedReader(new FileReader(somepath));
reader.readLine(); // this will read the first line
String line1=null;
while ((line1 = reader.readLine()) != null){ //loop will run from 2nd line
//some code
}
You can use the Stream skip() function, like this:
BufferedReader reader = new BufferedReader(new FileReader(somepath));
Stream<String> lines = reader.lines().skip(1);
lines.forEachOrdered(line -> {
...
});
File file = new File("path to file");
FileInputStream fis = new FileInputStream(file);
BufferedReader br = new BufferedReader(new InputStreamReader(fis));
String line = null;
int count = 0;
while((line = br.readLine()) != null) { // read through file line by line
if(count != 0) { // count == 0 means the first line
System.out.println("That's not the first line");
}
count++; // count increments as you read lines
}
br.close(); // do not forget to close the resources
Use a linenumberreader instead.
LineNumberReader reader = new LineNumberReader(new InputStreamReader(file.getInputStream()));
String line1;
while ((line1 = reader.readLine()) != null)
{
if(reader.getLineNumber()==1){
continue;
}
System.out.println(line1);
}
You can create a counter that contains the value of the starting line:
private final static START_LINE = 1;
BufferedReader reader = new BufferedReader(new FileReader(somepath));
int counter=START_LINE;
while ((line1 = reader.readLine()) != null) {
if(counter>START_LINE){
//your code here
}
counter++;
}
You can do it like this:
BufferedReader buf = new BufferedReader(new FileReader(fileName));
String line = null;
String[] wordsArray;
boolean skipFirstLine = true;
while(true){
line = buf.readLine();
if ( skipFirstLine){ // skip data header
skipFirstLine = false; continue;
}
if(line == null){
break;
}else{
wordsArray = line.split("\t");
}
buf.close();

How to convert FileInputStream into string in java?

In my java project, I'm passing FileInputStream to a function,
I need to convert (typecast FileInputStream to string),
How to do it.??
public static void checkfor(FileInputStream fis) {
String a=new String;
a=fis //how to do convert fileInputStream into string
print string here
}
You can't directly convert it to string. You should implement something like this
Add this code to your method
//Commented this out because this is not the efficient way to achieve that
//StringBuilder builder = new StringBuilder();
//int ch;
//while((ch = fis.read()) != -1){
// builder.append((char)ch);
//}
//
//System.out.println(builder.toString());
Use Aubin's solution:
public static String getFileContent(
FileInputStream fis,
String encoding ) throws IOException
{
try( BufferedReader br =
new BufferedReader( new InputStreamReader(fis, encoding )))
{
StringBuilder sb = new StringBuilder();
String line;
while(( line = br.readLine()) != null ) {
sb.append( line );
sb.append( '\n' );
}
return sb.toString();
}
}
public static String getFileContent(
FileInputStream fis,
String encoding ) throws IOException
{
try( BufferedReader br =
new BufferedReader( new InputStreamReader(fis, encoding )))
{
StringBuilder sb = new StringBuilder();
String line;
while(( line = br.readLine()) != null ) {
sb.append( line );
sb.append( '\n' );
}
return sb.toString();
}
}
Using Apache commons IOUtils function
import org.apache.commons.io.IOUtils;
InputStream inStream = new FileInputStream("filename.txt");
String body = IOUtils.toString(inStream, StandardCharsets.UTF_8.name());
Don't make the mistake of relying upon or needlessly converting/losing endline characters. Do it character by character. Don't forget to use the proper character encoding to interpres the stream.
public String getFileContent( FileInputStream fis ) {
StringBuilder sb = new StringBuilder();
Reader r = new InputStreamReader(fis, "UTF-8"); //or whatever encoding
int ch = r.read();
while(ch >= 0) {
sb.append(ch);
ch = r.read();
}
return sb.toString();
}
If you want to make this a little more efficient, you can use arrays of characters instead, but to be honest, looping over the characters can be still quite fast.
public String getFileContent( FileInputStream fis ) {
StringBuilder sb = new StringBuilder();
Reader r = new InputStreamReader(fis, "UTF-8"); //or whatever encoding
char[] buf = new char[1024];
int amt = r.read(buf);
while(amt > 0) {
sb.append(buf, 0, amt);
amt = r.read(buf);
}
return sb.toString();
}
From an answer I edited here:
static String convertStreamToString(java.io.InputStream is) {
if (is == null) {
return "";
}
java.util.Scanner s = new java.util.Scanner(is);
s.useDelimiter("\\A");
String streamString = s.hasNext() ? s.next() : "";
s.close();
return streamString;
}
This avoids all errors and works well.
Use following code ---->
try {
FileInputStream fis=new FileInputStream("filename.txt");
int i=0;
while((i = fis.read()) !=-1 ) { // to reach until the laste bytecode -1
System.out.print((char)i); /* For converting each bytecode into character */
}
fis.close();
} catch(Exception ex) {
System.out.println(ex);
}

readLine() null return

I have the following code:
public static void main(String[] args) throws Exception {
String s = "";
StringBuilder sb = new StringBuilder();
File file = new File("C:\\New\\r.txt");
BufferedReader in = new BufferedReader(new FileReader(file));
while(in.readLine() != null) {
sb.append(in.readLine());
}
System.out.println(sb);
s = sb.toString();
byte[] b = s.getBytes();
for(int i = 0; i < b.length; i++) {
if(b[i] == 1){ b[i]=0; }
if(b[i] == 0){ b[i]=1; }
}
FileOutputStream fos = new FileOutputStream(file);
DataOutputStream dos = new DataOutputStream(fos);
dos.write(b);
in.close();
fos.close();
dos.close();
}
I get a return of null when I run this program. Maybe I must elevate the program? Help would be appreciated.
Change:
while(in.readLine()!=null)
to:
while((s = in.readLine())!=null)
and then:
sb.append(s);
When you call in your code to in.readLine() twice - you're reading two lines but printing only the second in each iteration.
You're throwing away every odd line:
while(in.readLine()!=null)
{
sb.append(in.readLine());
}
If r.txt only contains one line, you will get the string "null" in the StringBuffer, because the first line of StringBuffer.append does this:
public AbstractStringBuilder append(String str) {
if (str == null) str = "null";
....
}
If there are two lines, you will get the first line with "null" at the end of the line.
The following will append all lines from the file to the StringBuffer:
String line = null;
while((line = in.readLine()) != null)
{
sb.append(line);
}
your code
while(in.readLine() != null) {
sb.append(in.readLine());
}
change with it
while ((s = in.readLine()) != null)
{
sb.append(s);
}

Categories

Resources