I want to write data to file when it's opened, but it doesn't work. Calendar getTime works nice, System.out.println() proves this. Please, any idea, what's wrong...?
Main class:
public static void main(String[] args) throws IOException {
// TODO code application logic here
CurrentTime ct = new CurrentTime();
}
CurrentTime class:
public class CurrentTime {
public OutputStream output;
public InputStream input;
public Process npp;
CurrentTime() throws IOException
{
Timer t = new Timer();
npp = Runtime.getRuntime().exec("notepad");
output = npp.getOutputStream();
TimerTask task = new TimerTask() {
#Override
public void run()
{
String dateStr = Calendar.getInstance(new Locale("ua", "UA")).getTime().toString();
System.out.println(dateStr);
try {
output.write(dateStr.getBytes());
output.flush();
} catch (IOException ex) {
Logger.getLogger(CurrentTime.class.getName()).log(Level.SEVERE, null, ex);
}
}
};
t.schedule(task, 1000, 2000);
}
}
Maybe this code is wrong in all, np. In this way, I want to discover this moment by any side, is it impossible at all?
UPDATE: it's not actual anymore but just for a note, that time I was trying to implement some kind of tailing operation to the text editor directly and now I understand how abnormal this idea was.. had to be implemented using totally other way of course.
Interesting:
Lets deal this in simple way.
1. Save a file test.txt somewhere.
2. Open that file and keep it opened
In Java write to this file (Standard Code)
FileWriter fw = new FileWriter(new FileOutputStream(new File("c:/test.txt")));
fw.write("ABC")
Now go to notepad file again. I normally used Textpad it does refresh automatically (by an alert) because we changed it behind the scene (In your case through Java).
I hope that will clarify a bit.
To be fare trying to excess the genric notepad exe doesn't gurrantee which file you will write in. I am not sure how windows deal with it because you can open 3 different files at one time and which one you will expect to have your data written through java???
You're doing it wrong - It's impossible. notepad absolutely ignores it's input while it's running (like most GUI-programs). If you want to show a textbox and write text in it, simply create one with Swing/SWT/...
If you just want to write into a file, just create a new PrintWriter and use it to write files: http://docs.oracle.com/javase/6/docs/api/java/io/PrintWriter.html
You shouldn't try to write through Notepad. Check out PrintWriter.
Related
I am given an assignment where we are not allowed to use a DB or libraries but only textfile for data storage.
But it has rather complex requirements, for e.g. many validations, because of that, we need to "access the db" (i.e. read the textfile) many times.
My question is: should I create a class like this:
class SomeRepository{
static ArrayList<Users> users = new ArrayList();
public SomeRepository(){
//instantiate this class on program load
//In constructor, we read the text file, instantiate and store everything inside the arraylist.
}
//public getOneUser(){ // for get methods, we don't read from text file at all }
/public save() { //text file saving code overhere }
}
Is this a good approach to solve the above problem? Currently, what we are doing is reading and writing to the text file every time we want to retrieve some data or write something new.
Wouldn't this be too expensive in terms of heap space memory? Or should I just read/write to the text file for every method?
public class IOManager {
public static void writeObjToTxtFile(String fileName, Object object) {
File file = new File(fileName + ".txt");//File will be created in the root directory where the program runs.
try (FileOutputStream fos = new FileOutputStream(file);
ObjectOutputStream oos = new ObjectOutputStream(fos);) {
oos.writeObject(object);
} catch (IOException e) {
e.printStackTrace();
}
}
public static Object readObjFromTxtFile(String fileName) {
Object obj = null;
File file = new File(fileName + ".txt");
FileInputStream fis = null;
try {
fis = new FileInputStream(file);
ObjectInputStream ois = new ObjectInputStream(fis);
obj = ois.readObject();
} catch (ClassNotFoundException | IOException e) {
e.printStackTrace();
}
return obj;
}
}
Add this class to your project. Since it's general for all Objects, you can pass and receive Objects like these as well: ArrayList<Users>. Play around and Tinker with it to fit whatever your specific purpose is. Hint: You can write other custom methods that calls these methods. eg:
public static void writeUsersToFile(ArrayList<Users> usersArrayList){
writeObjToTxtFile("users",usersArrayList);
}
Ps. Make sure your Objects implement Serializable. Eg:
public class Users implements Serializable {
}
I would suggest reading the contents of your file to a dynamic list such as an arraylist at the start of your program. Make the required queries/changes to your arraylist and then write that arraylist to your file when the program is set to close. This will save significant time over repeated file reads/writes.
This isn't without it's drawbacks, though. You don't want to hogg up memory in case of very large files - but considering this is an assignment, that may not be the case. Additionally, should your program terminate prior to the write at the end, all changes made to your database during the current execution will be lost.
I have a list of objects that has some simple String properties. I want to be able to save those strings to binary so that when you open the file outside the program, you only see 1's and 0's.
I have managed to use FileOutputStreamand saved the strings, however, I can't manage to get it to write to binary. The file reads as clean readable text. I have tried getBytes().
What would be the best approach for this? Keep in mind that I want to be able to read the file later and construct back the objects. Would it be better to use Serializable and save a list of objects?
Here is my FileWriter:
NB: The toString() is custom and returns a String with linebreaks for every property.
public class FileWriter {
public void write(String fileName, Savable objectToSave ) throws IOException {
File fileToSave = new File(fileName);
String stringToSave = objectToSave.toString();
byte[] bytesToSave = stringToSave.getBytes(StandardCharsets.UTF_8) ;
try (
OutputStream outputStream = new FileOutputStream(fileToSave);
) {
outputStream.write(bytesToSave);
} catch (IOException e) {
throw new IOException("error");
}
}
}
If your goal is simply serializing, implementing Serializable and writing them would work, but your string is still going to be readable. You can encrypt the stream, but anyone decompiling your code can still devise a way to read the values.
I am working on an Android App that changes the CPU Frequency when a foreground app changes. The frequencies for the foreground app is defined in my application itself. But while changing the frequencies my app has to open multiple system files and replace the frequency with my text. This makes my UI slow and when I change apps continuously, it makes the systemUI crash. What can I do to write these multiple files all together at the same time?
I have tried using ASynctaskLoader but that too crashes the SystemUI later.
public static boolean setFreq(String max_freq, String min_freq) {
ByteArrayInputStream inputStream = new ByteArrayInputStream(max_freq.getBytes(Charset.forName("UTF-8")));
ByteArrayInputStream inputStream1 = new ByteArrayInputStream(min_freq.getBytes(Charset.forName("UTF-8")));
SuFileOutputStream outputStream;
SuFileOutputStream outputStream1;
try {
if (max_freq != null) {
int cpus = 0;
while (true) {
SuFile f = new SuFile(CPUActivity.MAX_FREQ_PATH.replace("cpu0", "cpu" + cpus));
SuFile f1 = new SuFile(CPUActivity.MIN_FREQ_PATH.replace("cpu0", "cpu" + cpus));
outputStream = new SuFileOutputStream(f);
outputStream1 = new SuFileOutputStream(f1);
ShellUtils.pump(inputStream, outputStream);
ShellUtils.pump(inputStream1, outputStream1);
if (!f.exists()) {
break;
}
cpus++;
}
}
} catch (Exception ex) {
}
return true;
}
I assume SuFile and SuFileOutputStream are your custom implementations extending Java File and FileOutputStream classes.
Couple of points need to be fixed first.
f.exists() check should be before initializing OutputStream, otherwise it will create the file before checking exists or not. This makes your while loop to become an infinite loop.
as #Daryll suggested, use the number of CPUs with while/for loop. I suggest using for loop.
close your streams after pump(..) method call.
If you want to keep the main thread free, then you can do something like this,
see this code segment:
public static void setFreq(final String max_freq, final String min_freq) {
new Thread(new Runnable() {
//Put all the stuff here
}).start();
}
This should solve your problem.
Determine the number of CPUs before hand and use that number in your loop rather than using a while (true) having to do SuFile.exists() every cycle.
I don't know what SuFileOutputStream is but you may need to close those file output streams or find a faster way to write the file if that implementation is too slow.
I am writing a code in java to display text file in JTextArea. Can Anyone tell me what is wrong with this code. It is saying cannnot find symbol file..
FOpen.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent ae)
{
final JFileChooser FileDialog = new JFileChooser();
int ReturnValue=FileDialog.showOpenDialog(null);
if(ReturnValue==JFileChooser.APPROVE_OPTION)
{
File file = FileDialog.getSelectedFile();
}
BufferedReader in = new BufferedReader(new FileReader(file));
String line = in.readLine();
while(line!=null)
{
WritingArea.append(line+"\n");
line=in.readLine();
}
}
});
Look up 'variable scope/visibility'. Since the file attribute is declared inside the brackets, only code in that code block has access to it.
Other notes/tips:
If ReturnValue!= .. it does not make much sense to continue with the rest, so the rest of that method should also be inside the brackets.
That code will bloc the EDT for as long as it takes to load the File. Don't block the EDT (Event Dispatch Thread) - the GUI will 'freeze' when that happens. Instead of calling Thread.sleep(n) implement a Swing Timer for repeating tasks or a SwingWorker for long running tasks. See Concurrency in Swing for more details.
Please learn common Java naming conventions (specifically the case used for the names) for class, method & attribute names & use them consistently.
if WritingArea is a JTextComponent there is an easier way to load the data.
Always copy/paste error & exception output.
For better help sooner, post an SSCCE.
You really need to learn about scopes. Currently you File object is encapsulated in the if block's scope. If you want to use that File object anywhere else, it isn't allowed. So put everything into the if block, where they will be in the same scope as the File object
FOpen.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent ae)
{
final JFileChooser FileDialog = new JFileChooser();
int ReturnValue=FileDialog.showOpenDialog(null);
if(ReturnValue==JFileChooser.APPROVE_OPTION)
{
File file = FileDialog.getSelectedFile();
BufferedReader in = new BufferedReader(new FileReader(file));
String line = in.readLine();
while(line!=null)
{
WritingArea.append(line+"\n");
line=in.readLine();
}
}
}
});
I need to write something into a text file's beginning. I have a text file with content and i want write something before this content. Say i have;
Good afternoon sir,how are you today?
I'm fine,how are you?
Thanks for asking,I'm great
After modifying,I want it to be like this:
Page 1-Scene 59
25.05.2011
Good afternoon sir,how are you today?
I'm fine,how are you?
Thanks for asking,I'm great
Just made up the content :) How can i modify a text file like this way?
You can't really modify it that way - file systems don't generally let you insert data in arbitrary locations - but you can:
Create a new file
Write the prefix to it
Copy the data from the old file to the new file
Move the old file to a backup location
Move the new file to the old file's location
Optionally delete the old backup file
Just in case it will be useful for someone here is full source code of method to prepend lines to a file using Apache Commons IO library. The code does not read whole file into memory, so will work on files of any size.
public static void prependPrefix(File input, String prefix) throws IOException {
LineIterator li = FileUtils.lineIterator(input);
File tempFile = File.createTempFile("prependPrefix", ".tmp");
BufferedWriter w = new BufferedWriter(new FileWriter(tempFile));
try {
w.write(prefix);
while (li.hasNext()) {
w.write(li.next());
w.write("\n");
}
} finally {
IOUtils.closeQuietly(w);
LineIterator.closeQuietly(li);
}
FileUtils.deleteQuietly(input);
FileUtils.moveFile(tempFile, input);
}
I think what you want is random access. Check out the related java tutorial. However, I don't believe you can just insert data at an arbitrary point in the file; If I recall correctly, you'd only overwrite the data. If you wanted to insert, you'd have to have your code
copy a block,
overwrite with your new stuff,
copy the next block,
overwrite with the previously copied block,
return to 3 until no more blocks
As #atk suggested, java.nio.channels.SeekableByteChannel is a good interface. But it is available from 1.7 only.
Update : If you have no issue using FileUtils then use
String fileString = FileUtils.readFileToString(file);
This isn't a direct answer to the question, but often files are accessed via InputStreams. If this is your use case, then you can chain input streams via SequenceInputStream to achieve the same result. E.g.
InputStream inputStream = new SequenceInputStream(new ByteArrayInputStream("my line\n".getBytes()), new FileInputStream(new File("myfile.txt")));
I will leave it here just in case anyone need
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
try (FileInputStream fileInputStream1 = new FileInputStream(fileName1);
FileInputStream fileInputStream2 = new FileInputStream(fileName2)) {
while (fileInputStream2.available() > 0) {
byteArrayOutputStream.write(fileInputStream2.read());
}
while (fileInputStream1.available() > 0) {
byteArrayOutputStream.write(fileInputStream1.read());
}
}
try (FileOutputStream fileOutputStream = new FileOutputStream(fileName1)) {
byteArrayOutputStream.writeTo(fileOutputStream);
}