【问题标题】:Is there an easier alternative to mimicking the splat operator?模仿 splat 运算符是否有更简单的替代方法?
【发布时间】:2013-07-27 09:54:00
【问题描述】:

我发现它在 Ruby 中可用,但我从我在 Python 中所做的事情中认出了它; “splat”运算符。长话短说,我想知道是否有更简单的方法来完成我目前的工作,模仿“splat”操作员的工作。

我创建了一个其他人可以调用的中心方法,因为我意识到我有几个非常相似的方法,除了一些小事情之外,它们都在做同样的事情。这是方法签名:

private String callScript(String scriptLocation, String... extraArgs) throws Exception {

我想要求至少一个参数(scriptLocation),然后允许任意数量的额外参数。我最终要做的是创建一个ProcessBuilder。我的愿望是做这样的事情:

ProcessBuilder pb = new ProcessBuilder("something", scriptLocation, /* extraArgs */);

当然,ProcessBuilder 构造函数只接受如下内容:

  • List<String>
  • String[]
  • String...

所以我的方法显然行不通。

据我所知,我目前的解决方法是:

List<String> finalArgs = new ArrayList<String>();
finalArgs.add("something");
finalArgs.add(scriptLocation);
finalArgs.addAll(Arrays.asList(extraArgs));
ProcessBuilder pb = new ProcessBuilder(finalArgs);

(是的,我知道我不必使用List,可以只使用String[]

(是的,我知道我可以遍历extraArgs 并将它们单独添加到finalArgs,而不必使用addAllArrays.asList()

(是的,我知道我可以创建一个函数,通过返回某些与可变参数相结合的参数来有效地完成我的解决方法)

所以我猜除了这最后三个陈述之外,还有什么可以实现的吗?

【问题讨论】:

  • String... 实际上是String[]。如果您拆分 String s1String[] s2ToN 之类的参数以强制执行第一个参数,那么您唯一可以合并它们的方法是在新数组/列表中创建副本。
  • @zapl 对不起,我知道,但似乎我误解/过度思考了那部分。所以你基本上是说我目前的方法(以某种形式)真的是处理这个问题的唯一方法?如果是的话没问题,我只是不知道我是否遗漏了什么
  • 我不确定我是否理解这个问题...您正在寻找一种将一些字符串放入列表的更好方法?
  • @jtahlborn 我只是不知道是否有另一种方法可以“解包”可变参数(如 splat 运算符),而无需我将它们组合成一个列表/数组
  • 是的,没有其他方法可以解压/合并可变参数,因为每个array[] 的大小都是最终的。如果您需要添加一个元素,则必须创建一个更大的数组并在其中复制数据。 ArrayList 在内部做同样的事情。有一些方法可以使该操作比您更有效,但仅此而已。 (例如System.arraycopy()

标签: java arguments splat variadic-functions


【解决方案1】:

这取决于您对更简单的定义,但您可以使用 Builder 模式编写一个类:

public class MyProcessBuilder {
    List<String> args;

    MyProcessBuilder( String text, String location ) {
        args = new ArrayList<String>();
        args.add( text );
        args.add( location );
    }

    MyProcessBuilder arg( String arg ) {
        args.add( arg );
        return this;
    }

    MyProcessBuilder args( String... args ) {
        this.args.addAll( Arrays.asList( args ) );
        return this;
    }

    public ProcessBuilder go() {
        return new ProcessBuilder( args );
    }

    public static MyProcessBuilder callScript( String location ) {
        return new MyProcessBuilder( "something", location );
    }

    public static void main( String[] args ) {
        callScript( "/tmp/bla" ).arg( "something else" ).arg( "more" ).go();
    }
}

【讨论】:

  • 我不知道为什么我没有想到这样的事情,但这绝对是一个好建议;谢谢!
【解决方案2】:

当你打电话时

ProcessBuilder pb = new ProcessBuilder("something", scriptLocation, /* extraArgs */);

如果你有

public ProcessBuilder(String something, String scriptLocation, String... extraArgs);

那么你可以通过多种方式调用这个方法:

ProcessBuilder pb = new ProcessBuilder("something", "/tmp/script.sh");

ProcessBuilder pb = new ProcessBuilder("something", "/tmp/script.sh","someArg");

ProcessBuilder pb = new ProcessBuilder("something", "/tmp/script.sh","someArg","someArg2");



ProcessBuilder pb = new ProcessBuilder("something", "/tmp/script.sh");

ProcessBuilder pb = new ProcessBuilder("something", "/tmp/script.sh",new String[]{});

ProcessBuilder pb = new ProcessBuilder("something", "/tmp/script.sh",new String[]{"someArg"});

ProcessBuilder pb = new ProcessBuilder("something", "/tmp/script.sh",new String[]{"someArg","someArg2"});



ArrayList<String> someStringList = new ArrayList<String>();
someStringList .add("SomeArg");
someStringList .add("SomeArg2");
String[] extraArgs = someStringList .toArray(new String[someStringList .size()]);
ProcessBuilder pb = new ProcessBuilder("something", "/tmp/script.sh",extraArgs);

【讨论】:

    【解决方案3】:

    编写一个实用程序splat() 并发布它?:)

    这可能看起来更统一:

    List<String> finalArgs = new ArrayList<String>();
    
    finalArgs.addAll(Arrays.asList( "something" ));
    finalArgs.addAll(Arrays.asList( scriptLocation ));
    finalArgs.addAll(Arrays.asList( extraArgs )));
    
    ProcessBuilder pb = new ProcessBuilder(finalArgs);
    

    【讨论】:

      猜你喜欢
      • 2017-05-17
      • 2012-02-08
      • 1970-01-01
      • 1970-01-01
      • 2015-03-13
      • 1970-01-01
      • 2015-02-12
      • 2014-01-12
      • 2019-01-14
      相关资源
      最近更新 更多