I have a text file with the following contents:
one
two
three
four
I want to access the string "three" by its position in the text file in Java.I found the substring concept on google but unable to use it.
so far I am able to read the file contents:
import java.io.*;
class FileRead
{
public static void main(String args[])
{
try{
// Open the file that is the first
// command line parameter
FileInputStream fstream = new FileInputStream("textfile.txt");
// Get the object of DataInputStream
DataInputStream in = new DataInputStream(fstream);
BufferedReader br = new BufferedReader(new InputStreamReader(in));
String strLine;
//Read File Line By Line
while ((strLine = br.readLine()) != null) {
// Print the content on the console
System.out.println (strLine);
}
//Close the input stream
in.close();
}catch (Exception e){//Catch exception if any
System.err.println("Error: " + e.getMessage());
}
}
}
I want to apply the substring concept to the file.It asks for the position and displays the string.
String Str = new String("Welcome to Tutorialspoint.com");
System.out.println(Str.substring(10, 15) );
If you know the byte offsets within the file that you are interested in then it's straightforward:
RandomAccessFile raFile = new RandomAccessFile("textfile.txt", "r");
raFile.seek(startOffset);
byte[] bytes = new byte[length];
raFile.readFully(bytes);
raFile.close();
String str = new String(bytes, "Windows-1252"); // or whatever encoding
But for this to work you have to use byte offsets, not character offsets - if the file is encoded in a variable-width encoding such as UTF-8 then there's no way to seek directly to the nth character, you have to start at the top of the file and read and discard the first n-1 characters.
look for \r\n (linebreaks) in your text file. This way you should be able to count the rows containing your string.
your file in reality looks like this
one\r\n
two\r\n
three\r\n
four\r\n
You seem to be looking for this. The code I posted there works on the byte level, so it may not work for you. Another option is to use the BufferedReader and just read a single character in a loop like this:
String getString(String fileName, int start, int end) throws IOException {
int len = end - start;
if (len <= 0) {
throw new IllegalArgumentException("Length of string to output is zero or negative.");
}
char[] buffer = new char[len];
BufferedReader reader = new BufferedReader(new FileReader(fileName));
for (int i = 0; i < start; i++) {
reader.read(); // Ignore the result
}
reader.read(buffer, 0, len);
return new String(buffer);
}
Related
I have this code:
import java.io.*;
import java.nio.charset.StandardCharsets;
public class Main {
public static void main(String[] args) {
zero("zero.out");
System.out.println(zeroRead("zero.out"));
}
public static String zeroRead(String name) {
try (FileInputStream fos = new FileInputStream(name);
BufferedInputStream bos = new BufferedInputStream(fos);
DataInputStream dos = new DataInputStream(bos)) {
StringBuffer inputLine = new StringBuffer();
String tmp;
String s = "";
while ((tmp = dos.readLine()) != null) {
inputLine.append(tmp);
System.out.println(tmp);
}
dos.close();
return s;
}
catch (IOException e) {
e.printStackTrace();
}
return null;
}
public static void zero(String name) {
File file = new File(name);
String text = "König" + "\t";
try (FileOutputStream fos = new FileOutputStream(file);
BufferedOutputStream bos = new BufferedOutputStream(fos);
DataOutputStream dos = new DataOutputStream(bos)) {
dos.write(text.getBytes(StandardCharsets.UTF_8));
dos.writeInt(50);
} catch (IOException e) {
e.printStackTrace();
}
}
}
zero() method writes data into file: the string is written in UTF-8, while the number is written in binary. zeroRead() read the data from file.
The file looks like this after zero() is executed:
This is what zeroRead() returns:
How do I read the real data König\t50 from the file?
DataInputStream's readLine method has javadoc that is almost yelling that it doesn't want to be used. You should heed this javadoc: That method is bad and you should not use it. It doesn't do charset encoding.
Your file format is impossible as stated: You have no idea when to stop reading the string and start reading the binary numbers. However, the way you've described things, it sounds like the string is terminated by a newline, so, the \n character.
There is no easy 'just make this filter-reader and call .nextLine on it available, as they tend to buffer. You can try this:
InputStreamReader isr = new InputStreamReader(bos, StandardCharsets.UTF_8);
However, basic readers do not have a readLine method, and if you wrap this in a BufferedReader, it may read past the end (the 'buffer' in that name is not just there for kicks). You'd have to handroll a method that fetches one character at a time, appending them to a stringbuilder, ending on a newline:
StringBuilder out = new StringBuilder();
for (int c = isr.read(); c != -1 && c != '\n'; c = isr.read())
out.append((char) c);
String line = out.toString();
will get the job done and won't read 'past' the newline and gobble up your binary number.
I have to read from a text file and format the input. I'm new to java reading from files, and I don't know how to work with just some parts of what I read
Here is the initial file: http://pastebin.com/D0paWtAd
And I have to write in another file the following output:
Average,Joe,44,31,18,12,9,10
I've managed just to take everything from the file and print it to output. I would need help just in taking the output I need and print it to the screen. Any help is appreciated.
This is what I wrote up to now:
public class FileParsing {
public static String
read(String filename) throws IOException {
BufferedReader in = new BufferedReader(new FileReader("C:\\Users\\Bogdi\\Desktop\\example.txt"));
String s;
StringBuilder sb = new StringBuilder();
while((s = in.readLine())!= null) sb.append(s + "\n");
in.close();
return sb.toString();
}
If your goal is to do the specified output in another file you don't need to first get the content of your file in a StringBuilder before processing it, you can append the processed datas directly in a StringBuilder then you can write the result in a file. Here is an example that would work for the given file but you may have to modify it if the keys change in the future:
The following method will correctly process the datas from your file
public static String read(String filename) throws IOException {
BufferedReader in = new BufferedReader(new FileReader(filename));
String s;
StringBuilder sb = new StringBuilder();
while((s = in.readLine())!= null) {
String[] split1 = s.split("=");
if (split1[0].equals("name")) {
StringTokenizer tokenizer = new StringTokenizer(split1[1]);
sb.append(tokenizer.nextToken());
sb.append(",");
sb.append(tokenizer.nextToken());
sb.append(",");
} else if (split1[0].equals("index")) {
sb.append(split1[1] + ",");
} else if (split1[0].equals("FBid")) {
sb.append(split1[1]);
} else {
StringTokenizer tokenizer = new StringTokenizer(split1[1]);
String wasted = tokenizer.nextToken();
sb.append(tokenizer.nextToken() + ",");
}
}
in.close();
return sb.toString();
}
The next method will read any string to a file
public static void writeStringToFile(String string, String filePath) throws IOException {
BufferedWriter writer = new BufferedWriter(
new FileWriter(
new File(filePath)
)
);
writer.write(string);
writer.newLine();
writer.flush();
writer.close();
}
And here is a simple tests (File1.txt contains the datas from the file you shared on paste bin and I write them in another file)
public static void main(String[] args) throws Exception {
String datas = read("C:\\Tests\\File1.txt");
System.out.println(datas);
writeStringToFile(datas, "C:\\Tests\\FileOuput.txt" );
}
It will produce the exact output that you are expecting
[EDIT] #idk, apparently you have an exception executing my example, while it is working fine for me. That could only mean there is an error at data level. Here is the data sample that I used (and I believe I exactly copy the datas you shared)
And here is the result:
Good to know you are using "StringBuilder" component instead being concatenating your String values, way to go :).
More than knowledge on the Java.IO API to work with files, you will need some logic to get the results you expect. Here I came with an approach that could help you, not perfect, but can point you on how to face this problem.
//Reference to your file
String myFilePath = "c:/dev/myFile.txt";
File myFile = new File(myFilePath);
//Create a buffered reader, which is a good start
BufferedReader breader = new BufferedReader(new FileReader(myFile));
//Define this variable called line that will evaluate each line of our file
String line = null;
//I will use a StringBuilder to append the information I need
StringBuilder appender = new StringBuilder();
while ((line = breader.readLine()) != null) {
//First, I will obtain the characters after "equals" sign
String afterEquals = line.substring(line.indexOf("=") + 1, line.length());
//Then, if it contains digits...
if (afterEquals.matches(".*\\d+.*")) {
//I will just get the digits from the line
afterEquals = afterEquals.replaceAll("\\D+","");
}
//Finally, append the contents
appender.append(afterEquals);
appender.append(",");//This is the comma you want to include
}
//I will delete the last comma
appender.deleteCharAt(appender.length() - 1);
//Close the reader...
breader.close();
//Then create a process to write the content
BufferedWriter myWriter = new BufferedWriter(new FileWriter(new File("myResultFile.txt")));
//Write the full contents I get from my appender :)
myWriter.write(appender.toString());
//Close the writer
myWriter.close();
}
Hope this can help you. Happy coding!
I have a method to copy the entire file from one destination to another destination using buffer:
InputStream in = new FileInputStream(src);
OutputStream out = new FileOutputStream(dest);
byte[] buf = new byte[1024];
int len;
while ((len = in.read(buf)) > 0) {
out.write(buf, 0, len);
}
in.close();
out.close();
The file is in csv format:
"2280B_TJ1400_001","TJ1400_Type-7SR","192.168.50.76","Aries SDH","6.0","192.168.0.254",24,"2280B Cyberjaya","Mahadzir Ibrahim"
But as you can see it has quotes inside it. Is it possible remove them by based on my exisitng code???
Output should be like this:
2280B_TJ1400_001,TJ1400_Type-7SR,192.168.50.76,Aries SDH,6.0,192.168.0.254,24,2280B Cyberjaya,Mahadzir Ibrahim
If you use a BufferedReader you can use the readLine() function to read the contents of the file as a String. Then you can use the normal functions on String to manipulate it before writing it to the output. By using an OutputStreamWriter you can write the Strings directly.
An advantage of the above is that you never have to bother with the raw bytes, this makes your code easier to read and less prone to mistakes in special cases.
BufferedReader in = new BufferedReader(new InputStreamReader(new FileInputStream(src)));
OutputStreamWriter out = new OutputStreamWriter(new FileOutputStream(dest));
String line;
while ((line = in.readLine()) != null) {
String stringOut = line.replaceAll("\"", "");
out.write(stringOut);
}
in.close();
out.close();
Note that this removes all " characters, not just the ones at the start and end of each String. To do that, you can use a StringTokenizer, or a more complex replace.
Not sure it's a good idea or not, but you can do something like :
while ((len = in.read(buf)) > 0) {
String temp = new String(buf);
temp = temp.replaceAll("\"","");
buf = temp.getBytes();
len = temp.length();
out.write(buf, 0, len);
}
For me, I would read all the file before, in a String, and then strip out the ' " ' in the string. Then write it to the dest file.
Read the file in a string
I found this simple solution. This may not be the best depending on your level of error catching you need.But it's working enough ;)
String content = new Scanner(new File("filename")).useDelimiter("\\Z").next();
Stripout the ' " '
content = content.replaceAll('"', "");
Write it to dest file from here
Files.write(Paths.get("./duke.txt"), msg.getBytes());
This is for java 7+.
Did not test it but it should work !
Not necessarily good style, filtering quotes in binary data, but very solid.
Wrap the original InputStream with your own InputStream, filtering out the double quote.
I have added a quirk: in MS Excel a quoted field may contain a quote, which then is self-escaped, represented as two double quotes.
InputStream in = new UnquotingInputStream(new FileInputStream(src));
/**
* Removes ASCII double quote from an InputStream.
* Two consequtive quotes stand for one quote: self-escaping like used
* by MS Excel.
*/
public class UnquotingInputStream extends InputStream {
private final InputStream in;
private boolean justHadAQuote;
public UnquotingInputStream(InputStream in) {
this.in = in;
}
#Override
public int read() throws IOException {
int c = in.read();
if (c == '\"') {
if (!justHadAQuote) {
justHadAQuote = true;
return read(); // Skip quote
}
}
justHadAQuote = false;
return c;
}
}
Works for all encodings that use ASCII as subset. So not: UTF-16 or EBCDIC.
I mean , I want to delete line from my text on android. How can I delete?
I do not want to read one txt and create another with removing line. I want to delete line from my existing txt.
thanks.
This is a pretty tricky problem, despite it looking a trivial one. In case of variable lines length, maybe your only option is reading the file line by line to indentify offset and length of the target line. Then copying the following portion of the file starting at offset, eventually truncating the file lenght to its original size minus the the target line's length. I use a RandomAccessFile to access the internal pointer and also read by lines.
This program requires two command line arguments:
args[0] is the filename
args[1] is the target line number (1-based: first line is #1)
public class RemoveLine {
public static void main(String[] args) throws IOException {
// Use a random access file
RandomAccessFile file = new RandomAccessFile(args[0], "rw");
int counter = 0, target = Integer.parseInt(args[1]);
long offset = 0, length = 0;
while (file.readLine() != null) {
counter++;
if (counter == target)
break; // Found target line's offset
offset = file.getFilePointer();
}
length = file.getFilePointer() - offset;
if (target > counter) {
file.close();
throw new IOException("No such line!");
}
byte[] buffer = new byte[4096];
int read = -1; // will store byte reads from file.read()
while ((read = file.read(buffer)) > -1){
file.seek(file.getFilePointer() - read - length);
file.write(buffer, 0, read);
file.seek(file.getFilePointer() + length);
}
file.setLength(file.length() - length); //truncate by length
file.close();
}
}
Here is the full code, including a JUnit test case. The advantage of using this solution is that it should be fully scalable with respect to memory, ie since it uses a fixed buffer, its memory requirements are predictable and don't change according to the input file size.
Try storing file into a String buffer replace what you intend to replace, then replace the contents of the file entirely.
You can delete a line by copying the rest of the data in the file, then flushing the file and finally writing the copied data.Thr following code searches for the string to be deleted and skips the code to copy in a stringBuider . The contents of stringBuilder are copied to the same file after flushing
try {
InputStream inputStream = openFileInput(FILENAME);
FileOutputStream fos = openFileOutput("temp", Context.MODE_APPEND);
if (inputStream != null) {
InputStreamReader inputStreamReader = new InputStreamReader(inputStream);
BufferedReader bufferedReader = new BufferedReader(inputStreamReader);
String receiveString = "";
String deleteString = "<string you want to del>";
StringBuilder stringBuilder = new StringBuilder();
while ((receiveString = bufferedReader.readLine()) != null) {
if (!reciveString.equals(deleteline)) {
stringBuilder.append(receiveString);
}
}
fos.flush();
fos = openFileOutput(FILENAME, Context.MODE_PRIVATE);
fos.write(stringBuilder.toString().getBytes());
fos.close();
inputStream.close();
}
I am trying to read values from a text file. There are 6 doubles on each line for the file.
I created a getBufReader method
public BufferedReader getBufReader(String filename, int rawName){
if(D) Log.i(TAG, "GETTING FILE");
BufferedReader bufReader = null;
// open the file for reading
InputStream instream = getResources().openRawResource(rawName);
// if file the available for reading
if (instream != null) {
// prepare the file for reading
InputStreamReader inputreader = new InputStreamReader(instream);
bufReader = new BufferedReader(inputreader);
}
// close the file again
try{instream.close();}
catch (Exception e) {
if(D) Log.e(TAG, "Unable to Close " + filename);}
return bufReader;
}
Each line in the file is supposed to be an entire row in my 2D array. I tried to get a line, tokenize it and put that in the array. But the program keeps crashing. The DDMS Log does does not produce a bunch or errors as I expect
public void getData(){
int rawName = R.raw.values_doubles;
BufferedReader reader_0 = getBufReader(strData2, rawName );
//2D array of x rows and y columns to store the data
//
double[][] Data_temp = new double[size_x][size_y];
String line = null;
StringTokenizer Strtoken;
for(i=0;i<size_x;i++){
try {line = reader_0.readLine();}catch (IOException e) {}
if(line != null){
Strtoken = new StringTokenizer(line);
for(j=0;j<size_y;j++){
if (Strtoken.hasMoreTokens()){
Data_temp[i][j] = Double.parseDouble(Strtoken.nextToken());
CommandsAdapter.add(""+Data_temp[i][j]+" ");
}}
}
CommandsAdapter.add("\n");}}
Please help
Also, I get errors if I don't surroung reader_0.readLine() with try/catch.
I would create a FileInputStream and a Buffered Reader. I am writing this from my lap top so I cannot test this code but this should give you a general idea (my first app saved data on seperate lines in a text file and I could read and write to it using this method)
NOTE this requires you to know how many lines are in your file
FileInputStream fis = new FileInputStream(file);
BufferedReader reader = new BufferedReader(fis);
Double myArray[][] = new Double [Text_File_Lines][6];
StringBuffer buffer = new StringBuffer();
int x = 0;
int y = 0;
while (reader.readLine() != -1) { //indicating end of file
while (reader.nextChar != '\n' ) { //indicating new line
while (reader.nextChar != ' ' ) { //indicating no space character
buffer.append(reader.nextChar());
}
Double[y][x] = Double.parseDouble(buffer.toString()); //Parse double and add it to array
buffer = null; //restore buffer to null
x++;
}
y++;
}
PLEASE NOTE THIS IS VERY SLOPPY CODE THAT ALMOST DEFINITELY WONT WORK this is just to get you started and I will post my working code when I get home from work.