سؤال

This question already has an answer here:

I have a need for a "Runnable that accepts a parameter" although I know that such runnable doesn't really exist.

This may point to fundamental flaw in the design of my app and/or a mental block in my tired brain, so I am hoping to find here some advice on how to accomplish something like the following, without violating fundamental OO principles:

  private Runnable mOneShotTask = new Runnable(String str) {
    public void run(String str) {
       someFunc(str);
    }
  };  

Any idea how to accomplish something like the above?

هل كانت مفيدة؟

المحلول

You can declare a class right in the method

void Foo(String str) {
    class OneShotTask implements Runnable {
        String str;
        OneShotTask(String s) { str = s; }
        public void run() {
            someFunc(str);
        }
    }
    Thread t = new Thread(new OneShotTask(str));
    t.start();
}

نصائح أخرى

You could put it in a function.

String paramStr = "a parameter";
Runnable myRunnable = createRunnable(paramStr);

private Runnable createRunnable(final String paramStr){

    Runnable aRunnable = new Runnable(){
        public void run(){
            someFunc(paramStr);
        }
    };

    return aRunnable;

}

(When I used this, my parameter was an integer ID, which I used to make a hashmap of ID --> myRunnables. That way, I can use the hashmap to post/remove different myRunnable objects in a handler.)

theView.post(new Runnable() {
    String str;
    @Override                            
    public void run() {
        par.Log(str);                              
    }
    public Runnable init(String pstr) {
        this.str=pstr;
        return(this);
    }
}.init(str));

Create init function that returns object itself and initialize parameters with it.

I use the following class which implements the Runnable interface. With this class you can easily create new threads with arguments

public abstract class RunnableArg implements Runnable {

    Object[] m_args;

    public RunnableArg() {
    }

    public void run(Object... args) {
        setArgs(args);
        run();
    }

    public void setArgs(Object... args) {
        m_args = args;
    }

    public int getArgCount() {
        return m_args == null ? 0 : m_args.length;
    }

    public Object[] getArgs() {
        return m_args;
    }
}

You have two options:

  1. Define a named class. Pass your parameter to the constructor of the named class.

  2. Have your anonymous class close over your "parameter". Be sure to mark it as final.

I would first want to know what you are trying to accomplish here to need an argument to be passed to new Runnable() or to run(). The usual way should be to have a Runnable object which passes data(str) to its threads by setting member variables before starting. The run() method then uses these member variable values to do execute someFunc()

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top