I have a program in Java which use an helper class with static methods in the main class, as described:
public class MainClass {
public main() {
String abc = "xyz";
ResultA = Helper.methodA(abc);
ResultB = Helper.methodB(ResultA);
}
}
and the Helper:
public class Helper {
public static Result methodA(String s) {
...
}
public static Result methodB(Result r) {
...
}
}
Now, as you can see from the structure, there is a dependency of data between methodA and methodB in the helper, and I don't create any instance of class 'Helper'. Is that a proper use in static method as I have no validation of data here? Is there a better known structure for that case?
Would appreciate any help, thanks.
Better to use static methods as and when really needed. Utility classes having the static methods which share the common behaviour across the project.
If your method resides in the Utility class , then go ahead. Otherwise create object and access via in it.
Related
I have an interesting JUnit problem here (JUnit 4.12). I have a base class that only has static methods. They have to be static, because of the way they're used. I inherit other classes from the base class. So, if the base class is Base, we have ChildA and ChildB.
Most of the methods are contained in the base class, but it has to know which child it actually is (just calling the methods as the base class is invalid). This is done via a static data member in the base class:
public class Base {
protected static ChildType myType = ChildType.Invalid;
...
}
Each child sets the data member via a static initializer, thus:
static {
myType = ChildType.ChildA;
}
Then when the methods are called, the base class knows what type it is and loads the appropriate configurations (the type is actually a configuration name).
This all works perfectly when running the application. Stepping through it in the debugger and through log messages, I can see the appropriate types are set and the methods load the appropriate configurations based on the child type.
The problem arises when using JUnit. We have some JUnit tests to test each of the base class methods. Since calling the methods on just the base class is invalid, we call the methods on the child classes, thus:
bool result = ChildA.methodTwo();
This ''always fails''. Why? The static initializer never gets called. When running the code as an application, it gets called, and everyone is happy. When I run it as a JUnit test, the static initializer is skipped and the methods have invalid data. What is JUnit doing that skips the static initializer? Is there a way around it?
Details
In reality, we're not calling the method as I posted above. I just wanted the example to be as clear as possible. In reality, we have a Web Service written with the Jersey framework. The method called is one of the REST endpoints.
#POST
#Produces(MediaType.TEXT_PLAIN)
public String methodPost() {
...
return new String( itWorked ? "success" : "fail" );
}
And we call it like this (sorry about the ugly syntax, it's just the way it works):
#Test
public void testThePost() throws Exception {
javax.ws.rs.core.Response response = target("restapi/").request().post(Entity.entity(null, MediaType.TEXT_PLAIN));
assertEquals( 200, response.getStatus() );
}
All the GET tests work, and the static initializer is called on all of them. It's just this POST that fails, and only when running the JUnit test.
You are trying to implement polymorphic behavior for static methods, a language feature that is present in other programming languages, but is missing in Java.
[myType is] a protected member of the base class
Relying on static initializers to set static fields in the base class is very fragile, because multiple subclasses "compete" for a single field in the base class. This "locks in" the behavior of the base class into the behavior desirable for the subclass whose initializer ran last. Among other bad things, it denies a possibility of using multiple subclasses along with the Base class, and makes it possible for ChildA.methodTwo() to run functionality designed for ChildB.methodTwo(). In fact, there is no ChildA.methodTwo() and ChildB.methodTwo(), there's only Base.methodTwo() that relies on information prepared for it by the static initialization sequence.
There are several solutions to this problem. One possibility is to pass Class<Child###> object to methods of the base class:
class Base {
public static void method1(Class childConfig, String arg) {
...
}
public static void method2(Class childConfig, int arg1, String arg2) {
...
}
}
Now the callers would need to change
ChildA.method1("hello");
ChildA.method2(42, "world");
to
Base.method1(ChildA.class, "hello");
Base.method2(ChildA.class, 42, "world");
Another solution would be to replace static implementation with non-static, and use "regular" polymorphic behavior in conjunction with singletons created in derived classes:
class Base {
protected Base(Class childConfig) {
...
}
public void method1(String arg) {
...
}
public void method2(int arg1, String arg2) {
...
}
}
class ChildA extends Base {
private static final Base inst = new ChildA();
private ChildA() {
super(ChildA.class);
}
public static Base getInstance() {
return inst;
}
... // Override methods as needed
}
class ChildB extends Base {
private static final Base inst = new ChildB();
private ChildB() {
super(ChildB.class);
}
public static Base getInstance() {
return inst;
}
... // Override methods as needed
}
and call
ChildA.getInstance().method1("hello");
ChildA.getInstance().method2(42, "world");
There is only one Base.myType field shared amongst all accessors: Base, ChildA and ChildB. The following sequence of events could cause the failures you are seeing:
JUnit test invoking ChildA.methodOne() starts execution, causing the JVM classloader to load ChildA.class and execute its static initializer block, setting Base.myType to ChildType.ChildA,
JUnit test invoking ChildB.methodOne() starts execution, causing the JVM classloader to load ClassB.class and execute its static initializer block, setting Base.myType to ChildType.ChildB, then
JUnit test invoking ChildA.methodTwo() starts execution, not executing the ChildA static initializer block first as ChildA has already been loaded by the JVM classloader, resulting in the JUnit test failing because Base.myType (and thus ChildA.myType) presently equals ChildType.ChildB.
The basic design issue is that part of your code expects the child types to own the myType field but that field is in fact shared by all child types.
Please provide the order in which your JUnit tests are being run to verify the above theory. Thanks!
addendum: Thanks for clarifying in comments that you only have one JUnit test invoking just ChildA.methodTwo() which is only defined in Base, not ChildA. What is happening is likely the JVM deciding that ChildA need not be initialized just to call its parent Base class's methodTwo() method. #ShyJ provides a very nice explanation of this for parent and child static field access at https://stackoverflow.com/a/13475305/1840078. I believe that something similar is happening in your JUnit test.
addendum 2: Below is my code modeling and reproducing the described issue of myType having the value ChildType.Invalid during the JUnit test to the best of current understanding:
public enum ChildType {
Invalid, ChildA
}
public class Base {
protected static ChildType myType = ChildType.Invalid;
public static boolean methodTwo() {
return true;
}
}
public class ChildA extends Base {
static {
myType = ChildType.ChildA;
}
}
public class ChildATest {
#org.junit.Test
public void test() {
boolean result = ChildA.methodTwo();
System.out.println("result: " + result);
System.out.println("Base.myType: " + Base.myType);
}
}
Output of execution of ChildATest.test():
result: true
Base.myType: Invalid
I decided to try what #Arkdiy suggested and have pass-through methods in the child classes.
Let me reiterate: the code, as I had it, works perfectly when run as an application. Only when running via JUnit does it fail.
So now I have something similar to the below:
public class BaseClass {
protected static ChildType myType = ChildType.Invalid;
...
public static boolean methodTwoBase() {
...
}
}
public class ChildA extends BaseClass {
public static boolean methodOne() {
...
}
public static boolean methodTwo() {
myType = ChildType.ChildA;
return methodTwoBase();
}
}
public class ChildB extends BaseClass {
public static boolean methodOne() {
...
}
public static boolean methodTwo() {
myType = ChildType.ChildB;
return methodTwoBase();
}
}
Since I can't override static methods, the version of the method in the base class has a different signature (methodTwoBase() instead of methodTwo). I tried it as a regular application and in JUnit and it works both ways.
Kind of an interesting problem, and I blame JUnit. Thanks for all the input!
Why are static methods supported from Java 8? What is the difference between the two lines in main method in below code?
package sample;
public class A {
public static void doSomething()
{
System.out.println("Make A do something!");
}
}
public interface I {
public static void doSomething()
{
System.out.println("Make I do something!");
}
}
public class B {
public static void main(String[] args) {
A.doSomething(); //difference between this
I.doSomething(); //and this
}
}
As we can see above, I is not even implemented in B. What purpose would it serve to have a static method in an interface when we can write the same static method in another class and call it? Was it introduced for any other purpose than modularity. And by modularity, I mean the following:
public interface Singable {
public void sing();
public static String getDefaultScale()
{
return "A minor";
}
}
Just to put like methods together.
In the past, if you had an interface Foo and wanted to group interface-related utils or factory methods, you would need to create a separate utils class FooUtils and store everything there.
Those classes would not have anything in common other than the name, and additionally, the utils class would need to be made final and have a private constructor to forbid unwanted usage.
Now, thanks to the interface static methods, you can keep everything in one place without creating any additional classes.
It's also important to not forget all good practices and not throw everything mindlessly to one interface class - as pointed out in this answer
There are mainly two reasons for static method inside interfaces: create instances of those interfaces (and the code is clearly where it has to be); like Predicate::isEqual that would create a Predicate based provided Object; or Comparator::comparing, etc. And the second reason would be utility methods that are general per all those types; like Stream::of
Still an interface has to be clear and does not have to create additional clutter in the API. Even the jdk code has Collectors - static factory methods, but a Collector interface at the same time for example. Those methods could be merged into Collector interface, but that would make the interface more clunky than it has to be.
I'm a begginer programmer for Android and I found some code over the internet and I couldn't get what this "Class not meant to be instantiated" means?! Also what's the use of it. I would be very happy if somebody could help here.
public class Settings
{
//some code
private Settings() {} // Class not meant to be instantiated
//some code
}
The constructor is private so only the class itself can create instances. There are several reasons for doing this. A couple off the top of my head...
The class is a "utility" class that only contains static methods and so instantiating it would make no sense. As the class is commented "Class not meant to be instantiated" I guess this is the most likely reason.
The class itself controls its own lifecycle and provides methods for creating instances. For example if the class is a lazy singleton it might provide a method that creates an instance when first called and return this instance on subsequent calls.
It is a private constructor. This means that outside classes cannot create new instances using the default constructor.
A little more info
All Objects in Java have a default constructor:
public MyObject() {}
That is how you can have this class:
public class MyObject{}
and still be able to call:
MyObject mObj = new MyObject();
Private Constructors
Sometimes a developer may not want this default constructor to be visible. Adding any other constructor will nullify this constructor. This can either be a declared constructor with empty parameters (with any of the visibility modifiers) or it can be a different constructor all together.
In the case above, it is likely that one of the following models is followed:
The Settings object is instantiated within the Settings class, and is where all the code is run (a common model for Java - where such a class would also contain a static main(String[] args) method).
The Settings object has other, public constructors.
The Settings object is a Singleton, whereby one static instance of the Settings Object is provided to Objects through an accessor method. For example:
public class MyObject {
private static MyObject instance;
private MyObject(){}//overrides the default constructor
public static MyObject sharedMyObject() {
if (instance == null)
instance = new MyObject();//calls the private constructor
return instance;
}
}
This inner construct
private Settings() {}
is a constructor for Settings instances. Since it is private, nobody can access it (outside of the class itself) and therefore no instances can be created.
The constructor is private so its not meant to be called by anything outside of the class
It's not a nested class, it's a constructor. A private constructor means that you can't construct instances of this class from outside, like this:
Settings s = new Settings(); //Compilation error! :(
Now, if a class can't be instantiated, what could it be for? The most likely reason for this is that the class would return instances of itself from a static method, probably as a singleton. The settings are normally global to the program, so a singleton pattern really fits here. So there would be a static method that goes kind of like this
static private TheOnlySettings = null;
static public getSettings()
{
if(TheOnlySettings == null)
TheOnlySettings = new Settings(); //Legal, since it's inside the Settings class
return TheOnlySettings;
}
See if that's indeed the case.
As other have mentioned, a class having private constructors cannot be instantiated from outside the class. A static method can be used in this case.
class Demo
{
private Demo()
{
}
static void createObjects()
{
Demo o = new Demo();
}
}
class Test
{
public static void main (String ...ar)
{
Demo.createObjects();
}
}
We can have private constructor . Below program depicts the use of private constructor with a static function
class PrivateConstructor {
private:
PrivateConstructor(){
cout << "constructor called" << endl;
}
public:
static void display() {
PrivateConstructor();
}
};
int main() {
PrivateConstructor::display();
}
I have an abstract class type that I'm inheriting from to create new classes. As an equivalent example, consider:
public abstract class BaseClass {
public BaseClass(String input)
{
...
}
public abstract void doSomething();
public String getResult()
{
...
}
}
Now I can override BaseClass and implement "doSomething" to perform different actions (for example, reverse or capitalize, if I were really working with strings, though I'm not really, it's just an example).
The most common usage is:
BaseClass bc = new ExtendsBaseClass(input);
bc.doSomething();
String result = bc.getResult()
So I want to make a static wrapper method for this.
I'd like to implement:
public static String doSomethingForResult(String input)
{
BaseClass bc = /*new current type*/;
bc.doSomething();
return bc.getResult();
}
But I have no idea what to replace that comment with, or how to make it work; I don't want to force every implementing class to re-implement this (if that's even conceptually possible; since abstract static is not allowed.
Static methods are not polymorphic, and thus can't be inherited and overridden. What you want to do is impossible.
Why do you bother with static things in this case?
Just benefit from polymorphism and merge doSomething() and getResult().
You would end up with:
public abstract class BaseClass {
public BaseClass(String input)
{
...
}
public abstract String doSomething();
}
and your client would look like:
BaseClass bc = new ExtendsBaseClass(input);
String result = bc.doSomething();
In generally, defining a separated getResult() method would make sense in specific cases like in implementing Builder Pattern. Indeed, several distinct methods participate to the object construction and end up with a call to a kind of getResult() method.
---------------------After your comment just below------------------------
If, as you said, the common case was to use doSomething() follows by getResult() and depending on a specific subclass, you could use Template Method pattern:
public abstract class BaseClass {
public BaseClass(String input)
{
// assigments
}
public String process(){ //process is a template method
doSomething();
return getResult();
}
protected abstract void doSomething();
protected abstract String getResult();
}
public class ExtendedClass extends BaseClass {
protected void doSomething(){
//...
}
protected String getResult(){
//....
}
}
Your client would only call process() method:
BaseClass bc = new ExtendsBaseClass(input);
String result = bc.process();
But please :), avoid static things when possible, they aren't lead to a good OO programming.
So I want to make a static wrapper method for this.
I think I see why you might want to do this. You want a simple method to perform a common set of operations without having keep copying the boilerplate code again and again. But as you are painfully aware by now, static methods have no place in an inheritance hierarchy. I would recommend you get inspiration from the various Apache Commons projects and their XxxUtils classes which are composed solely of static methods and exist completely outside of the hierarchy of the classes they act on.
Consider the class FileUtils in Commons IO. It's just static methods but they are so helpful. Consider two methods:
static byte[] readFileToByteArray(File file) // Reads the contents of a file into a byte array.
static String readFileToString(File file) // Reads the contents of a file into a String
One methods deals with files and byte arrays, the other deals with files and strings? How do you know which does what - because it uses a descriptive name which spells it out. The are no inheritance, implementation, polymorphism issues because FileUtils exists completely outside the inheritance hierarchy of Files, Strings, byte arrays etc.
Let's get back to your hypothetical method. I would put this method in a separate class named MyUtils - or BitmapUtils and create a method for every combination of concrete classes that was meaningful.
public static String doSomethingWithExtendsBaseClass(String input)
{
BaseClass bc = new ExtendsBaseClass();
bc.doSomething();
return bc.getResult();
}
public static String doSomethingWithOtherClass(String input)
{
BaseClass bc = new OtherClass();
bc.doSomething();
return bc.getResult();
}
But I have no idea what to replace that comment with, or how to make it work
Simple - you just instantiate the concrete class directly in the method with the corresponding name.
I think you can define a static method in BaseClass and pass the other class as argument to it using BaseClass as argument class e.g.
public static String doSomethingForResult(String input ,BaseClass bc){
bc.doSomething();
return bc.getResult();
}
Then in your ExtendedBaseClass you may write as:
ExtendedBaseClass extendedBaseObject= new ExtendedBaseClass();
String result = BaseClass.doSomethingForResult("input", extendedBaseObject);
System.out.println(result);
Basically I have a class which an instance of is created via a Singleton class. The class should never been instantiated via any other means than the singleton class. My question is can the class be effectively 'not seen' by other classes, apart from Singleton.
I know inner classes and different pacakages etc would help, but I'm curious to see if anyone has a nice solution to this.
Thanks for replies
Just refactor class itself as singleton. Private constructor and etc.
An easy and efficient way to do Singleton with an Enum:
public enum Singleton {
INSTANCE;
public void execute (String arg) {
//... perform operation here ...
}
}
In a sample scenario, using your API, do I need to declare?:
ToBeInvisibleClass instance = TheSingleton.getThatInvisibleInstnace();
If the answer is Yes, then the answer to your question is No since I need to declare a variable and for that I need the type to visible. If the answer is No, then using inner/nested class seems to be a proper approach or making the class itself the singleton.
Java has no "friend" concept like C++
You mentioned nested classes (real inner classes will not work because they need the outer) and packages.
Other approaches to protected other classes but one from creating an instance are not known to me.
But in general there is no reason to build a singleton by an helper class.
You could build singleton using enums or static final vars
What is the best approach for using an Enum as a singleton in Java?
public enum Elvis implements HasAge {
INSTANCE;
private int age;
#Override
public int getAge() {
return age;
}
}
class X {
public static final X instance = new X ();
private X () {
}
...
}
To assure that instantiation only occurs through your class method, you can do the following:
Make the default constructor private
Save your singleton instance in a private method
Use a public static method to provide the instance to the clients:
In this site there's a nice example:
public class MySingleton {
private static MySingleton _instance = new MySingleton();
private MySingleton() {
// construct object . . .
}
public static MySingleton getInstance() {
return _instance;
}