I am planning out a Java application that will store information and pictures about items in my coin collection. For example, each coin will have its own record page. On that page there will be text fields where user-entered information will be shown, along with pictures of that particular coin. The user will have the options to add, remove, and update the records in this application.
My question is, how do I go about storing all of this data? Right now, I have most of the GUI designed and working properly. But I am unsure of the "correct" way to store and organize all the data and images for each record. Should I be pushing this data into an SQL database when the record is created and then pull from it when the user is browsing that record? Or should I create some sort of directory structure where each record has its own directory which contains the images and a text file of all the data fields?
Also, I plan to distribute this application to some of my friends so I want to make sure that everything will work correctly for them without having to install any other software (besides Java).
I am pretty new to writing these kinds of applications as I usually just write command-line scripts. Any help that anybody can provide will be greatly appreciated!
Thank you.
you can have a relational database like MySql with below basic schema.
Tables : Coins, user_entered_infos, Users
Coins - Id(PK), name, image_link
Users - Id(PK), first_name, second_name
user_entered_infos - Id(PK), coin_id(FK), user_id(FK), user_entered_info
In this way you can select for each coin you can select all the user entered information from user_entered_infos table and view it. And when user add or remove from the coin page remove it from the table.
A database may be overkill for your needs and is a whole learning-curve unto itself. You might get what you are after with some Java's built-in object serialization. Serialzation is an easy way to save your objects to a file or pass them to other applications.
Consider the following code a very simple sketch for how you might approach this problem. I'm sure you have much more detailed objects than what I am about to show you, this code's purpose is to give you an general idea for how to serialize an object and save it.
import java.io.*;
import java.util.ArrayList;
public class CoinCollectionApp {
static File collectionFile = new File("path/to/file/coin-collection.obj");
public static void main(String[] args) {
ArrayList<Coin> coins = new ArrayList<>();
Coin lincolnPenny = new Coin("Lincoln penny", 1955, "fine");
coins.add(lincolnPenny);
saveCollection(coins);
}
static void saveCollection(ArrayList<Coin> coinCollection) {
try {
FileOutputStream fout = new FileOutputStream(collectionFile);
ObjectOutputStream oos = new ObjectOutputStream(fout);
oos.writeObject(coinCollection);
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
static class Coin implements Serializable {
private static final long serialVersionUID = 1L;
String name;
int year;
String quality;
public Coin(String name, int year, String quality) {
this.name = name;
this.year = year;
this.quality = quality;
}
}
}
Related
Currently, I'm writing a RPG plugin. I've created a PlayerInfo class that stores the player's UUID, character class like knight and archer, and skills that modify a player's attributes, e.g. vitality would increase a players health, strength would increase a player's physical damage, and so on.
Here's the class so far:
public class PlayerInfo {
public String suuid;
public String charClass;
public int vitality;
public int strength;
public int defense;
public int dexterity;
public int intelligence;
public int faith;
public PlayerInfo() {
}
public PlayerInfo(String UUID, String characterClass, int VIT, int STR, int DEF, int DEX, int INT, int FAI) {
suuid = UUID;
charClass = characterClass;
vitality = VIT;
strength = STR;
defense = DEF;
dexterity = DEX;
intelligence = INT;
faith = FAI;
}
I'd like to say as well that I'm primarily a Python and Javascript programmer. I picked up Java about 2 days ago, so I apologize if my code is unhygienic. I'm still trying to understand the languages and its practices. If you would like, I'd appreciate any advice on that as well. Though, feel free to just answer my base question, as I will be posting to Code Review, too, at some point in the future.
Moving forward...
While working on the basic framework of this plugin, I've realized that the information within the PlayerInfo class is most likely not saved when the server is stopped. I thought that possibly I could write the information, using FileOutputStream and ObjectOutputStream, to a file, and store that in a config folder, and later retrieve it with the Input versions of those modules. However, I ran into an issue when trying to dynamically pick up the path of the jar file, as my server told me that my Access was denied when trying to create the folder and file.
My last issue comes when trying to use the loaded information. My plugin's commands start with /static. If I had a command named /static stats that displayed the users stats, would it be as simple as comparing the user's UUID to the one stored in the save file? For example:
Player player = (Player) sender;
String suuid = player.getUniqueId().toString();
if (character.suuid == suuid) {
// Load stats here...
}
Or is there a different way to go about doing it?
To condense my post down a bit:
How can I store Player and class information effectively, and how can I later retrieve that data to use for information and see if the current player matches a saved object? Is this what stuff like SQL is used for?
Load each player when they connect to the server into a memory (make a new PlayerInfo Object for each of them, using for example a HashMap or a List).
On player disconnect you have to save all the information into a file/database (sql included) which is being restored and loaded again on next connect of the given player.
The information is being lost when server stops, therefore you need to store it somewhere and retrieve it when you need it.
You can create a simple function to retrieve a PlayerInfo based on a HashMap
HashMap<String, PlayerInfo> allplayers = new HashMap<String, PlayerInfo>();
public PlayerInfo getPlayer(Player player){
if(allplayers.containsKey(player.getName())){
return allplayers.get(player.getName());
}else{
return null;
}
}
And to put players into a HashMap
public void addPlayer(Player player){
if(!allplayers.containsKey(player.getName())){
//Load playerInfo
PlayerInfo p = new PlayerInfo(....);
//put into hashmap
allplayers.put(player.getName(), p);
}
}
//saving PlayerInfo can be called on PlayerDisonnect/Server shutdown
public void savePlayer(Player player){
if(allplayers.containsKey(player.getName())){
PlayerInfo p = allplayers.get(player.getName());
//Save information
.....
//remove player from HashMap
allplayers.remove(player.getName());
}
} `
Okay , u can use serialization on your class , and i guess its the way cause u have just the primitives , and then u can byte write ur created serialization file to a sql database , and when u need it , u can again read it back and type cast it to ur class object . Then u can invoke an iterator to loop through the propertises and find matches for ur player with .equals method .
I'm in the process of developing a stat tracker for Baseball season. I'd like to be able to load an entire schedule ino the program, making each game a relatively simple object.
Creating the game object isn't an issue. What I'm wondering is, what's the best way to implement the schedule? I have, in the team class, an ArrayList schedule.
I need a way to load the schedule info from a text file, loop through it and create a game object for each line. If that's not the best way to create 162 objects efficiently, please let me know.
Cheers
EDIT:
The game class is really very simple:
public class Game implements Serializable{
Date gameDate;
Team team;
public int runsScored, runsAllowed;
public ArrayList<BallPlayer> lineup = new ArrayList<BallPlayer>();
public ArrayList<Pitcher> pitchers = new ArrayList<Pitcher>();
public Pitcher starter;
String opponent;
boolean homeAway;
boolean result;
public Game(Team gTeam, Pitcher gStarter, String gOpponent, String homeOrAway, Date gDate){
this.team = gTeam;
this.starter = gStarter;
this.opponent = gOpponent;
if(homeOrAway.equalsIgnoreCase("home")){this.homeAway = true;}
this.runsScored = 0;
this.runsAllowed = 0;
gameDate = gDate;
}
public String getOpponent(){return opponent;}
public void setOpponent(String o){this.opponent = o;}
public boolean getHomeAway(){return homeAway;}
public void setHomeAway(String ho){if(ho.equalsIgnoreCase("home")){this.homeAway = true;}else{this.homeAway = false;}}
}
This is a pretty general question but I thought I would give you some thoughts on how I would initially approach this.
For your models, you could start with something like this:
GameVO (id, home team id (TeamVO), away team id (TeamVO), location id, schedule_id)
TeamVO (id, mascot, name, hometown, etc.)
LocationVO (id, city, state, stadium name, etc.)
PlayerVO(id, position, fname, lname, number, team_id, array_of_stat_ids)
StatVO(id, game_id, player_id, base_hits, home_runs, rbi, strike_out, etc)
ScheduleVO(id, location_id, home_team_id, away_team_id, play_time)
For the text file, I would recommend becoming comfortable with Regular Expressions. Regular expressions allow you to read in strings of data and extract data based on the patterns that you specific. Your text file will either be a fixed-length text-file, comma separated values (CSV), or some other format (first make sure you understand how your data is structured). Once you have identified the patterns that you want to extract, create your regex to match on every line and extract the appropriate values. Here is a good place to practice with your Regex
Finally, when seriallizing your objects take a look at seriallizers like XStream for .NET. I liked the Java version of this library as it allows you to quickly turn java objects into XML/json and back again.
I am working on an android app that loads in a list of students to display in a list based activity. There are two components to the app. There is a server which responds via xml with the list of current active students and a database on the app end which stores theses students with some details (name,age etc). I would like a way to sync these two data sources. When the app starts, I would like to check against the xml to see if students on the server were added/deleted and update the db accordingly.
I would be parsing the xml list into a student object at login. Is there any way to store/retrieve an entire object into an android supported db so I can do a direct comparison to see what to update/delete? It would end up being something like
if (serverStudent[0].name == dbStudent[0].name)
//overwrite dbStudent object with serverStudent fields
What is the most efficient/lightweight way to achieve object persistance and then comparison in Android?
Here's a method I have used in the past:
Anytime an object in the database is changed, use a timestamp column to store that time. When the app connects on startup, simply check each timestamp in the app db against the timestamp in the server db for each object. If the timestamps match, do nothing. If the timestamps don't match, retrieve the updated record from the server. Make sure you're using a detail enough timestamp (usually down to milli- or micro- seconds).
The nice thing about timestamps is that if you don't want the server data to override the app data, you could look at which is newer and keep that object if they've both been edited. Just adding some additional thoughts!
You can do something like this -
public class StudentRecord {
Vector<StudentData> studentDatas;
public StudentRecord()
{
studentDatas = new Vector<StudentData>();
}
public Vector<StudentData> getRecords() {
return studentDatas;
}
public void setRecords(Vector<StudentData> records) {
this.studentDatas = records;
}
public class StudentData
{
String name,Rollno;
public String getRollno() {
return Rollno;
}
public void setRollno(String rollno) {
Rollno = rollno;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
}
When you get the vector object studentDatas you can do something like this -
for(Object object : record.getRecords())
{
data = (StudentData)object;
data.getRollno();
data.getName();
}
Check out these libraries:
http://www.datadroidlib.com/
https://github.com/octo-online/robospice
I believe both offer solutions for your situation.
Or you can roll your own solution... Basically you will want to create a service or asynctask to do the syncing, in your student object you can create a constructor that you can pass an id to and have it pull the appropriate record from your local db then make a comparison method that will update if newer information is available.
I'm not sure i understood your question correctly.But as far as i understand i would do something like this.
In server side send send Json array which holds json student objects.
In android side create similer Student class and override equals
method as you want.
Then for each student check with equals method whether they are
equals or not and take action accordingly.
If you want to make faster search in students object array then apply
hash map instead of arrays.
As it currently stands, this question is not a good fit for our Q&A format. We expect answers to be supported by facts, references, or expertise, but this question will likely solicit debate, arguments, polling, or extended discussion. If you feel that this question can be improved and possibly reopened, visit the help center for guidance.
Closed 9 years ago.
Me and some friends are making a top down shooter in Java and wanted to make it online we have set up a UDP socket connection which works fine but we aren't to sure about how to store data that we receive from the client.
at the moment we are using a number of hashmaps to store the data, for example we have three hashmaps for player tracking, game information (number of players etc) and bullets (bullet locations, who fired etc).
But I am sure that there must be a better more secure way of storing this data other than hashmaps but not to sure what.
edit thx- Philipp (Sorry it took so long for a half decent question)
My concern about using hashmaps to store this data is that there are quite a lot of data to be put into them and we are currently using a single row to store all data for a object for example a row in the player hashmap would have the player id as the key, with a string value to store anything else such as "hp,xloc,yloc". which we then split to use. Which I cant seem to think is the most efficient way to store and retrieve the data.
Sorry if this still doesn't make sense.
I suppose my real question is are there any alternatives that are more efficient or if the hashmap is the best way to go?
Thanks
As you figured out yourself, storing the data about each entity in the game in a string is not a good idea.
You have to parse the string whenever you need some information about it, and string parsing isn't very fast and can easily get pretty complicated when the data about each entity gets more complex.
A much better way to do this is to create a class for each entity type with a set of class variables and use this to store the data about each entity:
class Player {
public:
int positionX;
int positionY;
int lifes;
String name;
//...
}
(by the way: an experienced object-oriented programmer would declare these variables as private and use getter and setter methods for changing them, but let's not go that far for now)
Your hash maps would then store instances of this class:
HashMap<Integer, Player> players;
Setting these up is easy:
Player p = new Player();
p.positionX = 200;
p.positionY = 400;
p.lifes = 3;
p.name = "Ford Prefect";
players.put(42, p);
(By the way: An experienced OOP programmer would use a constructor)
You can set and get the variables of each player by accessing the hash map:
players.get(42).positionX += 10; // move player 42 10 pixels to the right
In-memory is fine. Unless you need to persist the data, don't worry about it.
However, "which we then split to use" is not fine. It's a micro-"optimization" that will actually be slower/less efficient: naught but pain and lost time lies down this route.
I don't know your particular setup, but consider this:
class Player {
public Player (int playerId) {
this.playerId = playerId;
}
// ID during game - not permanent; for link-back to Hash key
public final int playerId;
// Add methods and fields as appropriate
String name;
int health;
// position, armour color, fairy dust, etc.
}
// How ids are "connected" to players:
// playerId -> Player
Map<Integer,Player> players = new HashMap..;
// When a player "connects"
int playerId = getUniqueIdForGameInstance();
Player player = new Player(playerId); // setup other information as required
players.add(player.playerId, player);
// On attack ..
int attackerId = getAttackerFromClient();
int targetId = getTargetFromClient();
Player attacker = players.get(attackerId);
Player target = players.get(targetId);
target.getWumped(attacker.wumpStength());
The same can be applied for other entities in the game. Notice that the Map is used to be able to find a player given a particular ID, but an instance of the Player class holds information about the player.
Look at ProtocolBuffers for serialization across the wire.
Hashmaps are an ok solution - they're thread-safe, so assuming you don't have 10,000 users accessing your website at once, they should work for you.
However, at present all your data is stored in memory. This is a problem if the program terminates.
The simplest recommendation I can give it to write your HashMaps to a file. This is done in Java by adding the Serializable interface to your class declaration - however you do not need to do this for HashMap as it is already Serializeable. (You only have to do this for classes you have written that are stored in the HashMap.)
then just add the following to your main() method (to read from a file):
try {
FileInputStream fis = new FileInputStream("Game.sav");
ObjectInputStream ois = new ObjectInputStream(fis);
HashMap<K,V> loadedGame = (HashMap<K,V>) ois.readObject();
} catch (Exception e) {
// Create new hash maps (no HashMap files found)
}
and this to a saveGame() method that can be called at your discretion
try {
FileOutputStream fos = new FileOutputStream("Game.sav");
ObjectOutputStream oos = new ObjectOutputStream(fos);
o.writeObject(hashmapGameVariable);
o.close();
} catch (IOException ioe) {
ioe.printStackTrace(); // something went wrong, you may not have write premissions
}
Okay I'll try to be direct.
I am working on a file sharing application that is based on a common Client/Serer architecture. I also have HandleClient class but that is not particularly important here.
What I wanna do is to allow users to search for a particular file that can be stored in shared folders of other users. For example, 3 users are connected with server and they all have their respective shared folders. One of them wants to do a search for a file named "Madonna" and the application should list all files containing that name and next to that file name there should be an information about user(s) that have/has a wanted file. That information can be either username or IPAddress. Here is the User class, the way it needs to be written (that's how my superiors wanted it):
import java.io.File;
import java.util.ArrayList;
import java.util.Scanner;
public class User {
public static String username;
public static String ipAddress;
public User(String username, String ipAddress) {
username = username.toLowerCase();
System.out.println(username + " " + ipAddress);
}
public static void fileList() {
Scanner userTyping = new Scanner(System.in);
String fileLocation = userTyping.nextLine();
File folder = new File(fileLocation);
File[] files = folder.listFiles();
ArrayList<String> list = new ArrayList<String>();
for (int i = 0; i < files.length; i++) {
list.add(i, files[i].toString().substring(fileLocation.length()));
System.out.println(list.get(i));
}
}
public static void main(String args[]) {
System.out.println("Insert the URL of your shared folder");
User.fileList();
}
}
This class stores attributes of a particular user (username, IPAddress) and also creates the list of files from the shared folder of that particular user. the list type is ArrayList, that's how it has to be, again, my superiors told me to.
On the other hand I need another class that is called RequestForFile(String fileName) whose purpose is to look for a certain file within ArrayLists of files from all users that are logged in at the moment of search.
This is how it should look, and this is where I especially need your help cause I get an error and I can't complete the class.
import java.util.ArrayList;
public class RequestForFile {
public RequestForFile(String fileName) {
User user = new User("Slavisha", "84.82.0.1");
ArrayList<User> listOfUsers = new ArrayList();
listOfUsers.add(user);
for (User someUser : listOfUsers) {
for (String request : User.fileList()) {
if (request.equals(fileName))
System.out.println(someUser + "has that file");
}
}
}
}
The idea is for user to look among the lists of other users and return the user(s) with a location of a wanted file.
GUI aside for now, I will get to it when I fix this problem.
Any help appreciated.
Thanks
I'm here to answer anything regarding this matter.
There are lots of problems here such as:
I don't think that this code can compile:
for (String request : User.fileList())
Because fileList() does not return anything. Then there's the question of why fileList() is static. That means that all User objects are sharing the same list. I guess that you have this becuase you are trying to test your user object from main().
I think instead you should have coded:
myUser = new User(...);
myUser.fileList()
and so fileList could not be static.
You have now explained your overall problem more clearly, but that reveals some deeper problems.
Let's start at the very top. Your request object: I think it represents one request for one user with one file definition. But it needs to go looking in the folders of many users. You add the the requesting user to a list, but what about the others. I think that this means that you need another class responsible for holding all the users.
Anyway lets have a class called UserManager.
UserMananger{
ArrayList<User> allTheUsers;
public UserManager() {
}
// methods here for adding and removing users from the list
// plus a method for doing the search
public ArrayList<FileDefinitions> findFile(request) [
// build the result
}
}
in the "line 14: for (String request : User.fileList()) {" I get this error: "void type not allowed here" and also "foreach not applicable to expression type"
You need to let User.fileList() return a List<String> and not void.
Thus, replace
public static void fileList() {
// ...
}
by
public static List<String> fileList() {
// ...
return list;
}
To learn more about basic Java programming, I can strongly recommend the Sun tutorials available in Trials Covering the Basics chapter here.
It looks like you're getting that error because the fileList() method needs to returns something that can be iterated through - which does not include void, which is what that method returns. As written, fileList is returning information to the console, which is great for your own debugging purposes, but it means that other methods can't get any of the information fileList sends to the console.
On a broader note, why is RequestForFile a separate class? If it just contains one method, you can just write it as a static method, or as a method in the class that's going to call it. Also, how will it get lists of other users? It looks like there's no way to do so as is, as you've hard-coded one user.
And looking at the answers, I'd strongly second djna's suggestion of having some class that acts as the controller/observer of all the Users.