简体   繁体   English

如何同时读取和写入同一文件中的数据

[英]How to read and write data into same file simultaneously

I have read many a posts where-in they speak about reading and writing into the file NOT simultaneously using JavaME. 我已经阅读了许多帖子,其中他们谈到了读取和写入文件而不是同时使用JavaME。 I have a special use case scenarios where-in my log file (maybe full file or just portion of the file) is uploaded to the server on regular basis. 我有一个特殊的用例场景,其中我的日志文件(可能是完整文件或只是文件的一部分)定期上传到服务器。 This must continue without hampering the current logging of the application in this same file. 这必须继续,而不会妨碍当前在同一文件中记录应用程序。

The code sample is a under: 代码示例如下:

boolean writing = true;
boolean reading = true;
void main() {
    new Thread("THREAD-FILE-READ") {
        public void run() {
            InputStream instream = getFileInStream();
            if (null != instream) {
                while (reading) {
                    try {
                        try {
                            synchronized(READ_LOCK) {
                                READ_LOCK.wait();
                            }
                        } catch (InterruptedException ex) {
                            ex.printStackTrace();
                        }

                        if (writtenCharsLen > 0) {
                            byte[] bytes = new byte[writtenCharsLen];
                            instream.read(bytes, 0, writtenCharsLen);
                            System.out.println("Read="+new String(bytes));
                            bytes = null;
                            writtenCharsLen = 0;
                        }
                    } catch (IOException ioe) {
                        ioe.printStackTrace();
                    }
                }
            }
            closeStream(instream);
        }
    }.start();

    new Thread("THREAD-FILE-WRITE") {
        public void run() {
            OutputStream outstream = getFileOutStream();
            if (null != outstream) {
                while (writing) {
                    try {
                        byte[] str = randomString();
                        if (null != str) {
                            writtenCharsLen = str.length;
                            System.out.println("Write=" + new String(str));
                            outstream.write(str);
                            str = null;
                        }
                    } catch (IOException ex) {
                        ex.printStackTrace();

                    } finally {
                        notifyReadStream();
                    }

                    try {
                        synchronized(WRITE_LOCK) {
                            WRITE_LOCK.wait();
                        }
                    } catch (InterruptedException ex) {
                        ex.printStackTrace();
                    }
                }
            }
            closeStream(outstream );
        }
    }.start();

}

void notifyReadStream() {
    try {
        synchronized (READ_LOCK) {
            READ_LOCK.notify();
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
}

void notifyWriteStream() {
    try {
        synchronized (WRITE_LOCK) {
            WRITE_LOCK.notify();
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
}

In the above code I will replace sop-read and sop-write with proper calls to network IO methods. 在上面的代码中,我将用适当的网络IO方法调用替换sop-read和sop-write。

PS: Since this piece of code will run of multiple files and multitude of devices i need the modification as compressed as possible to keep my runtime heap as low as possible. PS:由于这段代码将运行多个文件和多个设备,我需要尽可能压缩修改,以保持我的运行时堆尽可能低。 Also this piece of code will run till the application life cycle hence closing and opening the file in middle is out of consideration. 此代码也将运行到应用程序生命周期,因此关闭并打开中间的文件是不可考虑的。

Present Undesired Result: The read and write threads are showing running sop's for read and write. 出现不需要的结果:读写线程显示正在运行的读写错误。 The read thread is reading from the position the writing thread has written. 读取线程从写入线程写入的位置读取。 I am not facing any exception in this code but the result is undesired. 我没有在此代码中遇到任何异常,但结果是不希望的。 I have also tried synchronizing read and write streams but that is throwing IllegalMonitorStateException 我也尝试过同步读写流,但是抛出IllegalMonitorStateException

Expected Result: Reading of the stream must be triggered after writing into the stream is completed, also the read thread must be able to read from any position in the file. 预期结果:在写入流完成后必须触发流的读取,读取线程也必须能够从文件中的任何位置读取。

Any help / pointers is useful? 任何帮助/指针都有用吗?

EDIT: I was able to synchronize the read and the write streams using different monitors but i still feel, i could have done better using single monitor. 编辑:我能够使用不同的显示器同步读取和写入流但我仍然觉得,我可以使用单个监视器做得更好。 Will try it sometime later. 稍后会尝试一下。

I will attack this problem: 我会解决这个问题:

Present Undesired Result : The read and write threads are showing running sop's for read and write. 出现不需要的结果 :读写线程显示正在运行的读写错误。 The read thread is reading from the position the writing thread has written. 读取线程从写入线程写入的位置读取。 I am not facing any exception in this code but the result is undesired. 我没有在此代码中遇到任何异常,但结果是不希望的。 I have also tried synchronizing read and write streams but that is throwing IllegalMonitorStateException . 我也尝试过同步读写流,但是抛出IllegalMonitorStateException

If you have synchronized the access using monitors ie the reader calls someObject.wait() and the writer calls someObject.notify() , remember that you have to wrap these calls in a synchronized block on someObject : 如果您已使用监视器同步访问,即读者调用someObject.wait()并且someObject.wait()器调用someObject.wait() someObject.notify() ,请记住您必须将这些调用包装在someObject上的synchronized块中:

synchronized(someObject) {
    someObject.wait();
}


synchronized(someObject) {
    someObject.notify();
}

This is the cause for IllegalMonitorStateException . 这是IllegalMonitorStateException的原因。

Your first problem is that you are setting writtenCharsLen before you write the data. 您的第一个问题是您在写入数据之前设置了writCharsLen。 If your read thread sees it being non-zero before the write thread actually writes it, you have a problem. 如果您的读线程在写线程实际写入之前看到它非零,那么您就会遇到问题。 Move writtenCharsLen = str.length after the write. 写入后移动writtenCharsLen = str.length。

Another problem I see in your sample is that the threads never yield control. 我在您的示例中看到的另一个问题是线程永远不会产生控制。 They will be CPU hogs. 他们将是CPU猪。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM