I have an arraylist of objects in a fragmentActivity
private List<Movie> myMovies = null;
I have options to add, remove and all that from the movie list, but once I close the application all is lost. How can I save the array into a file and retrieve the array from the file?
I have:
public void writeArray() {
File f = new File(getFilesDir()+"MyMovieArray.srl");
try {
FileOutputStream fos = new FileOutputStream(f);
ObjectOutputStream objectwrite = new ObjectOutputStream(fos);
objectwrite.writeObject(myMovies);
fos.close();
if (!f.exists()) {
f.mkdirs();
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public ArrayList<Movie> read(Context context) {
ObjectInputStream input = null;
ArrayList<Movie> ReturnClass = null;
File f = new File(this.getFilesDir(),"MyMovieArray");
try {
input = new ObjectInputStream(new FileInputStream(f));
ReturnClass = (ArrayList<Movie>) input.readObject();
input.close();
} catch (StreamCorruptedException e) {
e.printStackTrace();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
return ReturnClass;
}
but it is not working. getFilesDir() always points to a nullpointerexception
Is this the right way to do it?
Any sugestions on how can I save the array into a file and retrieve the array from the file?
UPDATE 1: Found the fix, just needed to write File f = new File(getFilesDir(), "MyMovieArray.srl");
New problem arrised: I have this code for onCreate:
myMovies = read(this);
if(myMovies==null){
myMovies = new ArrayList<Movie>();
populateMovieListWithExamples();
writeArray();
}
Everytime I start the application it always shows the list with the populate examples... if I add or remove once I reopen it is always the same list. Sugestions?
UPDATE 2 Just needed Movie class to be serializable. Thank you all for your help. Have a good day everyone
You are saving to MyMovieArray.srl but reading from MyMovieArray. Read also from MyMovieArray.srl
File object should be created like this (both in write and read):
File f = new File(getFilesDir(), "MyMovieArray.srl");
Use File f = new File(getFilesDir(), "MyMovieArray.srl");
in both writeArray() and read() methods
Related
I need to write/read an ArrayList<Marker> to a file.
Here is what I did so far:
Save List:
private void saveToFile(ArrayList<Marker> arrayList) {
try {
FileOutputStream fileOutputStream = openFileOutput("test.txt", Context.MODE_PRIVATE);
ObjectOutputStream out = new ObjectOutputStream(fileOutputStream);
out.writeObject(arrayList);
out.close();
fileOutputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
Load List
private ArrayList<Marker> loadFromFile() {
ArrayList<Marker> savedArrayList = null;
try {
FileInputStream inputStream = openFileInput("test.txt");
ObjectInputStream in = new ObjectInputStream(inputStream);
savedArrayList = (ArrayList<Marker>) in.readObject();
in.close();
inputStream.close();
} catch (IOException | ClassNotFoundException e) {
e.printStackTrace();
}
return savedArrayList;
}
When I run the code I'm getting ClassNotFoundException.
The issue is that I need to store the whole ArrayList<Marker> as object.
I have found a solution that it separates the Marker into lat/long and write it to the text file as numbers, but it is not suitable for me.
I understand that the Marker Class is not Serializable, but how then it can be saved as an whole object?
I am building an articles reading android application like TechChurn. I am fetching data from server in the form of json.
I am parsing Id(unique),title, author name and articles-content from json and displaying it in list-view.
Those parsed content is stored in local for accessing without internet access.
This i have done using a cache function.
Here is my code that is using for caching -
public final class CacheThis {
private CacheThis() {
}
public static void writeObject(Context context, String fileName,
Object object) throws IOException {
FileOutputStream fos;
ObjectOutputStream oos;
if (fileExistance(fileName, context)) {
fos = context.openFileOutput(fileName, Context.MODE_PRIVATE
| Context.MODE_APPEND);
oos = new AppendingObjectOutputStream(fos);
} else {
fos = context.openFileOutput(fileName, Context.MODE_PRIVATE
| Context.MODE_APPEND);
oos = new ObjectOutputStream(fos);
}
oos.writeObject(object);
oos.flush();
oos.close();
fos.close();
}
public static List<Object> readObject(Context context, String fileName) {
List<Object> list = new ArrayList<Object>(0);
FileInputStream fis;
try {
fis = context.openFileInput(fileName);
ObjectInputStream ois = new ObjectInputStream(fis);
Object object;
try {
while (true) {
object = ois.readObject();
list.add(object);
}
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
fis.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return list;
}
public static boolean fileExistance(String fname, Context context) {
File file = context.getFileStreamPath(fname);
return file.exists();
}
}
my article should be cached based on id instead its been loaded for every-time when app is started
Use the following methods to store and retrieve the data.. Here you can store the object..
private void writeData(Object data, String fileName) {
try {
FileOutputStream fos = context.openFileOutput(fileName,
Context.MODE_PRIVATE);
ObjectOutputStream os = new ObjectOutputStream(fos);
os.writeObject(data);
os.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public Object readData(String fileName){
Object data = null;
if (context != null) {
try {
FileInputStream fis = context.openFileInput(fileName);
ObjectInputStream is = new ObjectInputStream(fis);
data = is.readObject();
is.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (StreamCorruptedException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
return data;
}
Write the data once you got the response from the server(at first request to the server). Use the id as file name. After that check for the particular file before you want to hit server for data. If the file is available then you can get the data from that file, otherwise hit the server.
Honestly, I've searched a lot do this task so I ended up trying various methods but nothing worked until I ended up on this code. It works for me perfectly like it should, so I do not want to change my code.
The help I need is to put this code in a such a way that it begins to read a file, but if it the file doesn't exist then it will create a new file.
Code for saving data:
String data = sharedData.getText().toString();
try {
fos = openFileOutput(FILENAME, MODE_PRIVATE);
fos.write(data.getBytes());
fos.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
Code for loading data:
FileInputStream fis = null;
String collected = null;
try {
fis = openFileInput(FILENAME);
byte[] dataArray = new byte [fis.available()];
while (fis.read(dataArray) != -1){
collected = new String(dataArray);
}
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
try {
fis.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
So If I add the saving data code in to the "FileNotFoundException" catch of the loading data part then could I achieve what I want?
Add
File file = new File(FILENAME);
if(!file.exists())
{
file.createNewFile()
// write code for saving data to the file
}
above
fis = openFileInput(FILENAME);
This will check if there exists a File for the given FILENAME and if it doesn't it will create a new one.
If you're working on Android, why don't you use the API's solution for saving files?
Quoting:
String filename = "myfile";
String string = "Hello world!";
FileOutputStream outputStream;
try {
outputStream = openFileOutput(filename, Context.MODE_PRIVATE);
outputStream.write(string.getBytes());
outputStream.close();
} catch (Exception e) {
e.printStackTrace();
}
You should really read the whole document, they explain pretty well the basic ways of creating or accessing files, you can also check the different ways of storing data.
But regarding your original question:
So If I add the saving data code in to the "FileNotFoundException"
catch of the loading data part then could I achieve what I want?
Yes, you could achieve it.
Try this one:
public static void readData() throws IOException
{
File file = new File(path, filename);
if (!file.isFile() && !file.createNewFile()){
throw new IOException("Error creating new file: " + file.getAbsolutePath());
}
BufferedReader r = new BufferedReader(new FileReader(file));
try {
// ...
// read data
// ...
}finally{
r.close();
}
}
Ref: Java read a file, if it doesn't exist create it
I have an Android application and I would like to read and write an ArrayList<MyClass> to the Internal Storage.
The writing part works (I believe, haven't tested it yet :-) ) :
ArrayList<MyClass> aList;
public void saveToInternalStorage() {
try {
FileOutputStream fos = ctx.openFileOutput(STORAGE_FILENAME, Context.MODE_PRIVATE);
fos.write(aList.toString().getBytes());
fos.close();
}
catch (Exception e) {
Log.e("InternalStorage", e.getMessage());
}
}
But what I want to do now is read the whole ArrayList from the Storage and return it as an ArrayList like so:
public ArrayList<MyClass> readFromInternalStorage() {
ArrayList<MyClass> toReturn;
FileInputStream fis;
try {
fis = ctx.openFileInput(STORAGE_FILENAME);
//read in the ArrayList
toReturn = whatever is read in...
fis.close();
} catch (FileNotFoundException e) {
Log.e("InternalStorage", e.getMessage());
} catch (IOException e) {
Log.e("InternalStorage", e.getMessage());
}
return toReturn
}
I've never read in a file with Android before, so I don't know if this is even possible.
But is there A way I can read in my custom ArrayList?
you have to serialize/deserialize your object:
Your MyClass must implments Serializable and all the member inside MyClass must be serializable
public void saveToInternalStorage() {
try {
FileOutputStream fos = ctx.openFileOutput(STORAGE_FILENAME, Context.MODE_PRIVATE);
ObjectOutputStream of = new ObjectOutputStream(fos);
of.writeObject(aList);
of.flush();
of.close();
fos.close();
}
catch (Exception e) {
Log.e("InternalStorage", e.getMessage());
}
}
to deserialize the object:
public ArrayList<MyClass> readFromInternalStorage() {
ArrayList<MyClass> toReturn;
FileInputStream fis;
try {
fis = ctx.openFileInput(STORAGE_FILENAME);
ObjectInputStream oi = new ObjectInputStream(fis);
toReturn = oi.readObject();
oi.close();
} catch (FileNotFoundException e) {
Log.e("InternalStorage", e.getMessage());
} catch (IOException e) {
Log.e("InternalStorage", e.getMessage());
}
return toReturn
}
i'm trying to save a list of integers in my application by saving each integer in a new line of a file in the internal storage.
For retreiving it I read it line by line and put every linevalue, parsed as integer, in my list of integers.
I know a database is better for this kinda stuff, but this should work.
I am trying for quite a while now, but it never seems to work. I always get a nullpointerexception when trying to read. I logged "line", it gave the value it should have. But
saving one id, adding it as a new string:
private void saveToFavorites(Integer saveFav) {
String favstr = String.valueOf(saveFav);
BufferedWriter writer = null;
try {
writer = new BufferedWriter(new OutputStreamWriter(openFileOutput("favorites", MODE_WORLD_WRITEABLE)));
writer.newLine();
writer.append((favstr));
System.out.println(" added to favs :"+ saveFav);
} catch (Exception e) {
e.printStackTrace();
} finally {
if (writer != null) {
try {
writer.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
And the reading method:
#SuppressWarnings("null")
private List<Integer> readFileFromInternalStorage() {
List<Integer> favs = null;
BufferedReader input = null;
try {
input = new BufferedReader(new InputStreamReader(openFileInput("favorites")));
String line;
while ((line = input.readLine()) != null) {
System.out.println("readFileFromInternalStorage line value: "+ line );
favs.add(Integer.parseInt(line));
}
} catch (Exception e) {
e.printStackTrace();
System.out.println("readFileFromInternalStorage: fail" );
} finally {
if (input != null) {
try {
input.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return favs;
}
Which is in an other activity. I thought it would work but it clearly doesnt. When reading back, the logline: System.out.println("readFileFromInternalStorage line value: "+ line );
displays that the value of line equals the LAST added id,and an empty line, and not the others too. So the line by line saving fails. Also when parsing it to an integer it fails, what is weird because it is only a number.
08-01 12:29:54.190: I/System.out(1540): readFileFromInternalStorage line value:
08-01 12:29:54.190: I/System.out(1540): readFileFromInternalStorage line value: 301
Anyone knows what i need to change?
Since Integer is Serializable I sugget to serialize the entire List:
private void saveList(List<Integer> list) {
try {
File file = Environment.getExternalStorageDirectory();
File filename = new File(file, "yourfilename");
fos = new FileOutputStream(filename);
out = new ObjectOutputStream(fos);
out.writeObject(list);
out.close();
} catch (IOException ex) {
ex.printStackTrace();
}
}
private void readList()
{
try {
File file = Environment.getExternalStorageDirectory();
File filename = new File(file, "yourfilename");
fis = new FileInputStream(filename);
in = new ObjectInputStream(fis);
List<Integer> list= (List<Integer>) in.readObject();
in.close();
} catch (IOException ex) {
ex.printStackTrace();
} catch (ClassNotFoundException ex) {
ex.printStackTrace();
}
}
try this May it help you :-
1 - String saveFav = contaains all integer this form I1+"/"I2+"/"I3;
2:- then save it into file
private void saveToFavorites(String saveFav) {
//right here your code for write into file saveFave string
}
in reading file read string and split("/").it's working for me .
Here's some working code that will read and write ints to the phones internal memory.
You can create an array or list of ints and basically just iterate over it until all ints are saved/read to/from the memory:
Here's the code to write an int to the memory:
public void writePrimitiveInternalMemory(String filename, int value) {
SharedPreferences preferences = this.getPreferences(Activity.MODE_PRIVATE);
SharedPreferences.Editor editor = preferences.edit();
editor.putInt(filename, value);
editor.commit();
}
Here's code to read from the memory:
public int readPrimitiveInternalMemoryInteger(String filename) {
SharedPreferences preferences = this.getPreferences(Activity.MODE_PRIVATE);
return preferences.getInt(filename, 0);
}
I hope this helps you!
You are not allocating the integer list...
List<Integer> favs = null;
Allocate a new arraylist..
List<Integer> favs = new ArrayList<Integer>();