Suppose that I have a text file and I want to insert a character in each of its line at some position. Then can I insert a character there without rewriting all the characters ahead of that position with one position ahead.

Like, if I try to do that in C/C++ then before adding a character in the middle of a text file then we need to move all characters ahead of that position with one position so I do not loose any character.

So, is it possible in java to do it without moving rest of the characters.

Recommended Answers

All 21 Replies

If I understand the question then, no.
It's nothing to do with what language. If you put a new character into a file then either it overwrites an existing char or you have to move the rest up to make space for it.

Then it will take huge time if I have a very large text file. Is there any alternative to this, that is time efficient?

How big is "very large"? As long as it's under, say 100Meg, you could just read it into memory, update it there, write it back. As long as its under 2Gig you would have to read/write on the fly. Either way it's going to run as fast as your disk can read and write.

If this really is a big problem you should look at a better file structure, eg each line = 1 record, each record has a pointer to the next. Then you can update a line by writing the new version to the end of the file and updating the relevant pointer in place.

commented: awesome answer :) +3

Thanks for this answer, you explained very detail of it, it is just under 100Meg.

And if there is no difference with languages in this aspect then do you think writing it in C/C++ would be better choice than Java, for performance and efficiency gains?

Like I said, provided it's coded sensibly (esp. use buffered streams) it will be limited by your disk hardware read/write speed. The only way to improve beyond that would be a disk upgrade (SSD).
IMHO the "best" choice of language would be "the one you are most comfortable writing in". Performsnce/efficiency of the language won't be an issue.

Thank you for clearing my doubts :)

Correct: It's an operating system issue, not a language issue.

And pretty much all operating systems work this way.

And C/C++ won't be any faster at doing this than Java.

Really,
If you intend to do that a lot, inserting of characters/lines "in the middle of" text files quite often, then you need a file better design, not a "better" programming language.

Ok, if it is like that. Then it means that C/C++ are more efficient and and we can say fast only in processing of certain algorithms nothing else.

Correct me if i am getting it wrong.

C/C++ give the programmer access to more of the "low level" details of the CPU. So in theory a good programmer should be able to write faster and more efficient programs in C++ than in Java. But you have to be a pretty darn good programmer to do it. Doing so will take more time and cost more money.

Java also has a pretty severe disadvantage of having a long startup time.

But Java does a much better job at runtime optimization than C/C++ can. It "knows" more about the details of the actual CPU and hardware that is being used -- something that the C/C++ compiler typically isn't told. And the Java runtime Just-In-Time (JIT) compiler/optimizer has information about what code is actually present and its runtime patterns of usage than a C/C++ compiler could have.

So for big processes that run a long time, Java will generally be faster than C++.

commented: yes or not depends of desing, skills, ideas +9
commented: neatly explained +3

C/C++ give the programmer access to more of the "low level" details of the CPU. So in theory a good programmer should be able to write faster and more efficient programs in C++ than in Java. But you have to be a pretty darn good programmer to do it. Doing so will take more time and cost more money.

Java also has a pretty severe disadvantage of having a long startup time.

But Java does a much better job at runtime optimization than C/C++ can. It "knows" more about the details of the actual CPU and hardware that is being used -- something that the C/C++ compiler typically isn't told. And the Java runtime Just-In-Time (JIT) compiler/optimizer has information about what code is actually present and its runtime patterns of usage than a C/C++ compiler could have.

So for big processes that run a long time, Java will generally be faster than C++.

Thanks, it is a nice answer clearing long running doubts in my mind :)

I was just wondering that, in a file if we want to insert a character or string then we first need to shift all data further. And it does take some time atleast half minute or so for a file as big as around 40-50 pages.

But how does software like notepad,wordpad etc. accomplish this task that they shift everything instantly, likewise we have TextArea, TextField which can also shift everything instantly if we insert anything in between our data?

Because they are just updating an in-memory buffer, not reading/writing the file every time (that only happens on a Save)

I am giving my java code that I used to insert tabs at a specific column in an entire text file. It is working fine but only with one problem that just before that tab it also inserts a space on its own. It is not the case only with tabs, if I choose any other character to insert still it inserts a space before it. I looked it at multiple times but can't find any problem which can lead to this behavior.

I am attaching two text files that I used with program. One is the original copy before using this program and the other one is after using this. You can see a space before all tabs inserted in the file.

public class GetMeTabs {
    public static void main(String args[]) throws IOException{
        BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
        
        System.out.print("Enter File Name Along With Its Extension(like abc.txt) : ");
        String fName=br.readLine();
        System.out.print("Enter Column Number At Which You Want To Insert Tabs : ");
        int col=Integer.parseInt(br.readLine());
        br.close();
        
        System.out.println("\nPlease wait...\n\n");
        
        RandomAccessFile file=new RandomAccessFile(fName,"rwd");
        int fileLength=(int) file.length();
        long lineBeg=0;
        boolean finish=false;
        String s,q;
        
        while(finish!=true){    
            file.seek(col+lineBeg);         //Position pointer where you have to start copying to make room for new char
            int rem=(int) (fileLength-(col+lineBeg));
            
            byte[] takeData=new byte[rem];  //make byte array of size required into which data is to be copied
            file.readFully(takeData);       //read rest of file from position where we fixed pointer above
            
            file.seek(lineBeg+col);     //Place pointer back again to position where new char is to be inserted
            file.writeChar('\t');       //Insert specified char
            file.write(takeData);       //write the copied data back again after inserting char

            file.seek(lineBeg);             //Place pointer back on line begining for function below to skip that complete line
            fileLength=(int) file.length();     //Calcualte again the file size after adding char
            if((s=file.readLine())!=null){
                long ofFirstLine=file.getFilePointer();
                
                if(fileLength==ofFirstLine)
                    break;
                
                if((q=file.readLine())!=null){
                    if(q.length()<col){
                        if(q.length()<1)
                            lineBeg=ofFirstLine+2;
                    }
                    else
                        lineBeg=ofFirstLine;
                }
                else
                    lineBeg=ofFirstLine;
            }
            else
                break;
        }
        System.out.println("WE ARE DONE...");
        file.close();
    }
}

Why +2 on line 41?

Why +2 on line 41?

Because when it encounters a line without anything on it, so to skip that line.

It's not a space. It's an ASCII "null" character; a byte value zero.

The problem is that the "RandomAccessFile.writeChar" method is not doing what you think. JavaDoc says "Writes a char to the file as a two-byte value, high byte first. The write starts at the current position of the file pointer."

Change it to '.writeByte' and it will work.

Why +2 on line 41?

Looks like a Windows OS dependency to me. ;)

("New line" on Windows is "\r\n".)

It's not a space. It's an ASCII "null" character; a byte value zero.

The problem is that the "RandomAccessFile.writeChar" method is not doing what you think. JavaDoc says "Writes a char to the file as a two-byte value, high byte first. The write starts at the current position of the file pointer."

Change it to '.writeByte' and it will work.

Wow, how did you got there. I mean how did you found out that it is an byte zero character?
I also had a look at JavaDocs but didn't paid much attention to what does it really mean by high order and low order bits..

Thanks for the solution it is working good now :)

Looks like a Windows OS dependency to me. ;)

("New line" on Windows is "\r\n".)

I got the issue, actually I was walking on C/C++ steps and using readChar() and writeChar() to read and write characters but readByte() and writeByte() works best for doing it in the raw form.. Now instead to going through readLine() way I can now detect new line occurrences with readByte()

Wow, how did you got there. I mean how did you found out that it is an byte zero character?

I happened to look at the text file in eclipse. It showed a box, not a space.

From a number of different views it looked just like a space. Actually, I could not prove that it was a null. But given the environment, that seemed likely. Also it helps to keep in mind that in Java, the 'char' type is always two bytes.

Reading the JavaDoc for the method made it clear that it was a null character.

I happened to look at the text file in eclipse. It showed a box, not a space.

From a number of different views it looked just like a space. Actually, I could not prove that it was a null. But given the environment, that seemed likely. Also it helps to keep in mind that in Java, the 'char' type is always two bytes.

Reading the JavaDoc for the method made it clear that it was a null character.

Okk..I overlooked this thing. I need to look at problems more deeply. And I am using Netbeans,here it is looking like a space.

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.