I'm not quite sure how to do this, but I find myself using a list of lists quite often in this particular project. I think I'd like to refactor this into it's own collection. Basically, it's a list of users and their attributes. The object I'm using is a List<List<String>>. I think I'd like to make a drop-in replacement that maybe extends ArrayList and call it UserList or something similar.
Note: my only real goal is to keep from typing List<List<String>> everywhere.
What would be the best approach to take with this?
EDIT: Thanks. I guess I knew something could be better. Just couldn't quite put my finger on it. I had initially avoided creating a User class because I wasn't sure how I would easily be able to iterate over the attributes.
There is no need to create a custom List<List<String>> for these requirements.
Create a User class to store all the attributes, then create a List<User>.
You shouldn't.
You'll spend a lot more time writing this new class than just typing a few extra characters.
If you really want to make a new class.
Why not like this?
public class User {
private String attribute1;
private String attribute2;
//etc.
public String getAttribute1() {
return attribute1;
}
public void setAttribute1(String value) {
attribute1 = value;
}
public String getAttribute2() {
return attribute2;
}
public void setAttribute2(String value) {
attribute2 = value;
}
//etc.
}
If you insist on using nested Lists.
I suggest creating a wrapper class that would look something like this:
public class Users {
private List<List<String>> twoDList;
public String get(int x, int y) {
return twoDList.get(y).get(x);
}
public void set(int x, int y, String value) {
twoDList.set(y, twoDList.get(y).set(x, value));
}
//etc.
}
Related
I have been struggling to grasp this concept in Java. I have a list of objects I need to print. Either a string or bitmap. Each has its own way to be printed. My current interface would look like this:
public interface IPrintJob {
void print();
}
I have PrintJobText, and PrintJobBitmap classes which each implements IPrintJob. I need to be able to add them both to the same list. Can I do it with
ArrayList<IPrintJob> printjobs
Is this the right approach ? Should this be done with generics ? How would PrintJobText/PrintJobBitmap classes look ? I'm a bit lost after trawling the net for an understanding on the best way to handle this.
One example could be like this.. (not completely sure what you mean with a bitmap in this case though, so just made it a boolean)
public interface IPrintJob {
void print();
}
public class PrintJobText implements IPrintJob {
private String text;
PrintJobText(String text) {
this.text = text;
}
void print() {
System.out.println(text);
}
}
public class PrintJobBitmap implements IPrintJob {
private boolean bit;
PrintJobBitmap(boolean bit) {
this.bit = bit;
}
void print() {
System.out.println(bit ? "true" : "false");
}
}
List<IPrintJob> printjobs = new ArrayList<>();
printJobs.add(new PrintJobText("test1");
printJobs.add(new PrintJobBitmap(true);
printJobs.forEach(IPrintJob::print);
Of course the implementation of the print method can be anything. The system out is just an example.
Depends on what you mean by
Each has its own way to be printed
in my opinion. If you just mean what this answer demonstrates, you could also simply override toString() in both of the classes like this:
public class PrintJobText {
private String text;
PrintJobText(String text) {
this.text = text;
}
#Override
public String toString() {
return text;
}
}
public class PrintJobBitmap {
private boolean bit;
PrintJobBitmap(boolean bit) {
this.bit = bit;
}
#Override
public String toString() {
return String.valueOf(bit);
}
}
And simply store the objects in a List<Object> or some other common super-class.
Now does that mean you should do it this way? Probably not. At least don't store the objects in a List<Object>, because what if you wanted to add more functionality to your interface down the line?
Not only would you need to refactor a bunch of type definitions, but before the change nothing would have stopped you from adding instances of classes to the list that don't make any sense to be there, so now you either have to figure out a way to implement the new methods for those classes as well or restructure your code so those classes never get added to the list in the first place.
Another pitfall is that classes could forget to override toString() because there's no way to enforce them to do so.
Another possible definition of the interface could like this:
public interface IPrintJob {
String getPrintValue();
}
This would cut both the problems I mentioned above and is slightly cleaner than having a void print() as it removes the duplication of System.out.println(...) in the implementations.
Create a custom class that could contain attributes of either a string or a bitmap to contain the relevant object but under a different guise I guess, you can then create an array list of these custom objects, and use if ( object instanceof string ) then // do string code, and vice versa for bitmaps.
While creating JUnit test cases, it takes a long time to reconstruct objects for every single one of them and perform some operations that all my unit tests use.
Is there anyway I can make some objects in a test case that I can freely use in all of my tests without recreating them each time?
Thanks in advance!
A simple way of doing this is to create a private method that creates test objects. These can take in the parameters (the ones that need to change in the various test cases), or just provide a default object that you could in turn change. If the same objects are used in multiple tests, then a testdata-builder might be what you are looking for.
Say you have a class like this:
public class Something {
private String someString;
private Integer someInt;
public Something(final String someString, final Integer someInt) {
this.someString = someString;
this.someInt = someInt;
}
//getters and stuff
}
Then you can create a testdata builder like this:
public class SomethingBuilder {
private String someString;
private Integer someInt;
public SomethingBuilder() {
someString = "Some default value";
someInt = 42;
}
public SomethingBuilder withSomeString(final String someString) {
this.someString = someString;
return this;
}
public SomethingBuilder withSomeInt(final Integer someInt) {
this.someInt = someInt;
return this;
}
public Something build() {
final Something something = new Something(someString, someInt);
return something;
}
}
Then, creating test data becomes really simple, you can mutate the fields you different than your default values easily:
final Something something =
new SomethingBuilder().withSomeString("I want to override the default!").build();
Might seem like a bit of overkill for my small, example class, but if you have a central data class that appears in many tests, it will save you a lot of time and lines of code.
I am so new to Java world so please be kind.
I have one class which has some properties as below:
public class Test{
private long prop1;
private long prop2;
public long getProp1() {
return prop1;
}
public void setProp1(long prop1) {
this.prop1= prop1;
}
public long getProp2() {
return prop2;
}
public void setProp2(long prop2) {
this.prop2 = prop2;
}
}
Now I am after some operation I have filled object of class Test which is going to be sent to oData for save purpose. Somehow I do not want prop2 to be inserted into the string which will go to oData call, so how can I drop prop2 along with its value?
[prop1=1, prop2=2]
You will need a method that elaborate that for you,
one option can be define a method and print the properties as you need...
you can as orientation, take a look to this autogenerated toString method
#Override
public String toString() {
return "_Foo [prop1=" + prop1 + ", prop2=" + prop2 + "]";
}
remove the _Foo part and there you are!
thing is I require prop2 till one level to perform some operation but I need to remove it just before oData call, is it possible?
Not that I am aware of. Also, I don't know oData and your question is a bit hard to answer with the little info you provided. However, based on the above comment, I'm going to suggest two things:
Approach #1: Reduced Class
public class Test {
private long prop1;
private long prop2;
/* getters, setters, ...*/
}
public class TestReduced {
private long prop1;
public TestReduced(Test test) {
this.prop1 = test.getProp1();
}
/* getters, setters, ...*/
}
In other words, create a class that is similar to Test, bar the undesired member. In its constructor, copy every other member of the handed in Test object, effectively creating a copy that can be used for oData:
Test test1 = new Test();
test1.setProp1(1337L);
test1.setProp2(1007L);
/* Do something with test1, including prop2 */
TestReduced test2 = new TestReduced(test1);
/* Do oData stuff with test2, no prop2 anymore */
That's a pretty convoluted solution and it requires you to mirror all changes to Test in TestReduced. A common interface or an abstract base class could safeguard this process quite well, so I would definitely recommend putting one into place if you go with this. You should also consider adding a private constructor without parameters for TestReduced to make sure those can only be created from Test objects. Alternatively, let the Test class create instances of TestReduced with a method like getReducedInstance(), which would make Test a factory.
Approach #2: Member Map
How about, instead of having two members, prop1 and prop2, you use a Map?
public class Test {
private HashMap<String, Long> props = new HashMap<>();
public Test() {
props.put("prop1", 0L);
props.put("prop2", 0L);
}
public void setProp1(long prop1) {
props.put("prop1", p);
}
public void setProp2(long prop2) {
props.put("prop2", p);
}
public long getProp1() {
props.get("prop1");
}
public long getProp2() {
props.get("prop2");
}
public void prepareForSerialization() {
props.remove("prop2");
}
}
Whether this works with oData, I don't know. But it surely is a pretty flexible way to handle an arbitrary number of properties. With your getters and setters, you can hide the implementation (HashMap vs. primitive type memebers). Or, if you prefer, you can expose it to the user by providing methods like getProp(String name) and setProp(String name, long value). All of this is assuming that all your props are of type long.
Obviously, it would be better if you just had two methods for your serialization (?) purposes, one that includes prop1, one that doesn't. But since you explicitly said that you need to remove a member, this is what comes to my mind.
I'm trying to write a web service method that has a an object as one of it's parameters and that object has a property that is another object type. There seems to be no problem with passing in a object as long as all of the objects properties are primitive types. As soon as one of the properties is another object it has issues even if that embedded object is made of all primitives.
I'm using SoapUI to test it and the error I get is org.xml.sax.SAXException: No deserializer for {http://WebService}MyEmbeddedObject
I'm thinking there must be an easy way to tell it to deserialize the embedded object too but can't for the life of me figure out how. At this point I'll take the hard way too I just need a solution, I can always try to improve it later.
The method in the web service I'm writing looks like this:
public boolean MethodName(MyObject object, String sessionID) throws Exception
{
//do Stuff
}
The MyObject Class looks like this:
public class MyObject implements java.io.Serializable
{
public String Description;
public MyEmbeddedObject Thing1;
public MyEmbeddedObject Thing2;
public MyEmbeddedObject[] Things;
}
The MyEmbeddedObject Class looks like this:
public class MyEmbeddedObject implements java.io.Serializable
{
public String SubThing1;
public String SubThing2;
public String SubThing3;
}
In my case this problem had nothing to do with implementing java.io.Serializable. In fact you could remove that and it will work just fine as long as you fix the actual problem.
The actual problem being that you can't use an object as an argument unless all of it's properties are primitive types UNLESS you also use that embeded object in the method itself. It seems to be some sort of compiler voodoo if you ask me but here's the solution in code. Hopefully this makes sense. I'll even take it one level deeper just for illustration purposes.
One thing you'll notice that I've changed in the solution is that the "MyEmbeddedObject" class is much more complicated looking. This is because I didn't know how to properly define arrays in java at the time I asked this question. I assumed it was the same as C# and unfortunately for me that compounded my problem but I eventually figured it out by banging my head long enough and reviewing sample code from the vendor this project is for.
Program
public boolean MethodName(MyObject object, String sessionID)
{
//do Stuff
}
public MyEmbeddedObject unusedMyEmbeddedObject()
{
return null;
}
public MyDoubleEmbeddedObject unusedMyDoubleEmbeddedObject()
{
return null;
}
In a separate class file
public class MyObject
{
public String description;
public MyEmbeddedObject thing1;
public MyEmbeddedObject thing2;
}
In a separate class file
public class MyEmbeddedObject
{
public MyDoubleEmbeddedObject subThing1;
private MyDoubleEmbeddedObject[] subThings;
public MyDoubleEmbeddedObject[] getSubThings()
{
return this.subThings;
}
public void setSubThings(final MyDoubleEmbeddedObject[] value)
{
this.subThings = value;
}
}
In a separate class file
public class MyDoubleEmbeddedObject
{
public String subSubString1;
public String subSubString2;
public String subSubString3;
}
I have e.g. object like this:
Original obj = new Original();
And I use from this object e.g. method like(this object has many methods and fields):
obj.getMeYourName();
And I would like to have similar object which is almost same but some methods return something else. I want to solve it by facade.
So, at first I want to create facade and decided if I would return direct object or modified.
What is the best way?
Something like this: ?
Original obj = new Original();
OriginalFacade obj = new OriginalFacade(Original obj, boolean getDirectObject);
OriginalFacade(Original obj, boolean getDirectObject) {
if (getDirectObject) {
return obj //How to convert object into OriginalFacade type?
} else {
obj.setMeYourName("Something else");
return obj; //Howto convert object into OriginalFacade type?
}
}
So, I have 2 problems:
1, is it good solution choose original object or modified original object thru constructor with e.g. boolean getDirectObject?
2, how to easy return original object which must me mapped into OriginalFacade Object
Must I have implement all methods from original object?
Actually, the facade pattern uses a common interface that is used by clients.
For instance:
public interface Facade {
public String getMeYourName();
public void someOtherMethod();
}
public class Original implements Facade {
private String name;
Original(String name) {
this.name = name;
}
public String getMeYourName() {
return name;
}
public void someOtherMethod() {
// a lot of great code
}
}
public class Modified implements Facade {
private Facade original;
private String otherName;
Modified(Facade original, String otherName) {
this.original = original;
this.otherName = otherName;
}
public String getMeYourName() {
return otherName;
}
public void someOtherMethod() {
original.someOtherMethod();
}
}
The clients should only need to see the Facade interface, and shouldn't need to care which actual implementation they are dealing with.
Your code demonstrates you have not understood Facade at all.
In first place Facade should be used to provide a simple interface to complex algorithms.
Second, the facade pattern allows you to access its composed objects, for example:
public class OriginalFacade{
public Original original;
}
Unless you follow the Law of Demeter, this code is perfect valid.
Regardless, if Facade is used, you should not need to access those objects.
The following link explains a little bit of Facade
I recommend you buy and read this book
Facade is not the patter to be used here. It is used to make a complex interface simpler, for example, making out-of-the-box usage patterns.
In your case, why don't you just extend the Original class and overload the methods you want to behave differently?