0
abstract class A {
  protected abstract int isRunning();

  public void concreteMethod() {
    synchroinzed(isRunning()) {
       //do stuff
    }
  }
}

class B extends A {
  int running_ = 0;

  public int isRunning() {
     return running_;
  }
}

The problem I get: int is not a valid type's argument for the synchronized statement. How do I do this?

rolve
  • 10,083
  • 4
  • 55
  • 75
stackoverflow
  • 18,348
  • 50
  • 129
  • 196

6 Answers6

3

If you want to prevent simultaneous execution of your block and the method isRunning(), you can't do it exactly as you want because synchronization can't be inherited (only an implementation can justify synchronization).

Here's the nearest you can do :

class A {
  protected Object lock = new Object();
  protected abstract int isRunning();
  public void concreteMethod() {
    synchronized(lock) {
       //do stuff
    }
  }
}

class B extends A {
  int running_ = 0;    
  public int isRunning() {
    synchronized(lock) {
     return running_;
    }
  }
}

If you can afford to lock the entire concreteMethod() and not just a block, you have the simple solution to add the synchronized keyword to the concreteMethod and isRunning():

class A {
  protected abstract int isRunning();
  public synchronized void concreteMethod() {
       //do stuff
  }
}

class B extends A {
  int running_ = 0;    
  public synchronized int isRunning() {
     return running_;
  }
}
Sufian
  • 6,405
  • 16
  • 66
  • 120
Denys Séguret
  • 372,613
  • 87
  • 782
  • 758
1

You cannot have a lock on primitive value (int in your case since isRunning() returns an int).

Try to replace int by Integer for instance.

Mik378
  • 21,881
  • 15
  • 82
  • 180
1

Here is what the official documentation say

Another way to create synchronized code is with synchronized statements. Unlike synchronized methods, synchronized statements must specify the object that provides the intrinsic lock

Meaning, for synchronization you would first need an object to lock on. Since int is not an object you get an error. An Integer object would not give this error but just using an Integer instead of int would not guarantee correctness.

Here is a very good tutorial on java concurrency

http://tutorials.jenkov.com/java-concurrency/index.html

Ravi Bhatt
  • 3,147
  • 19
  • 21
  • ok lets forget its being synchronized on a integer. then what if the synchronizing was on a boolean – stackoverflow Oct 22 '12 at 14:43
  • 1
    Any primitive types would not work as a synchronization construct. A Boolean would work and not boolean. – Ravi Bhatt Oct 22 '12 at 14:48
  • The answer to "why can't we use `Integer` instead?" is described here very well http://stackoverflow.com/a/659939/1276636 – Sufian May 29 '14 at 11:14
1

I think you are confusing two concepts. Synchronized block always asks for reference as its parameter time but you are passing int (primitive data type ) as its argument. You can try using 'this' keyword (in place of isRunning() method) as synchronized block parameter. Also you need to declare class A as abstract. Also there is a spelling mistake in your code. You can also consider @dystroy 's solution.

Mohit Sehgal
  • 825
  • 1
  • 9
  • 26
0

I guess you are looking for this:

class A
{
  protected abstract int isRunning();

  public synchronized void concreteMethod()
  {
       //do stuff
  }
}

class B extends A
{
  int running_ = 0;

  public synchronized int isRunning()
  {
   return running_;
  }

}
Hakan Serce
  • 11,198
  • 3
  • 29
  • 48
0

- sychronized block is accompanied by an Object whose lock is needed to be obtained to access that block by the thread of execution.

- int is a primitive type and not an object.

- Creating an sychronized block along with an Object of the Super-Class is well accessible by its Sub-Classes.

Eg:

public void concreteMethod()
  {
    synchroinzed(A.class) // or synchroinzed(A.class)
    {
       //do stuff
    }
  }
Kumar Vivek Mitra
  • 33,294
  • 6
  • 48
  • 75