任何人都有参考va_listx86_64 ABI(在Linux上使用的那个)的表示?我正在尝试调试一些代码,其中堆栈或参数似乎已损坏,这将真正有助于理解我应该看到的内容......
我猜测,出于兼容性原因,vararg参数的类型Any*是Array [Any] - 如果我错了,请更正.但是,这并不能解释以下错误:
class Api(api_url: String, params: Seq[(String, String)]) {
def this(api_url: String, params: (String, String)*)
= this(api_url, params.seq)
}
Run Code Online (Sandbox Code Playgroud)
此代码无法编译,但会发出警告:
double definition:构造函数Api:(api_url:String,params:(String,String)*)Api和构造函数Api:(api_url:String,params:Seq [(String,String)])第13行的Api在擦除后具有相同的类型:(api_url:java.lang.String,params:Seq)Api
那么如何定义一个采用varargs或序列的构造函数呢?
如果我有一个va_list,我知道如何提取它的所有元素:
void printInts(int n,...)
{
va_list va;
va_start(va, n);
for(unsigned int i=0; i<n; i++)
{
int arg=va_arg(va, int);
printf("%d",arg);
}
va_end(va);
}
Run Code Online (Sandbox Code Playgroud)
因此,当我调用printInts(3,1,2,3)时,va_list将填充所有参数.
但是如何在不使用va_start的情况下手动填充va_list?我的意思是我想要这样的东西:
va_list va;
push_arg(va, int, 5); // And so on until I fill all parameters
...
Run Code Online (Sandbox Code Playgroud)
我需要这个,因为有一个函数接受va_list作为参数,我不知道如何填充其所有参数的va_list.
使用Stream.of创建通用流非常方便,但是如果我想创建一个Stream<String[]>只有一个元素呢?
比方说我有:
String[] tropicalFruits = new String[] {"pineapple", "banana", "mango"};
String[] fruits = new String[] {"melon", "peach", "apple"};
Run Code Online (Sandbox Code Playgroud)
然后Stream.of(tropicalFruits, fruits)产生Stream<String[]>两个元素.如何为单个元素的流实现相同的功能?如果我尝试:
Stream<String[]> fruityStream = Stream.of(tropicalFruits);
Run Code Online (Sandbox Code Playgroud)
我明白了:
错误:不兼容的类型:推理变量
T具有不兼容的边界
相等约束:java.lang.String[]
下限:java.lang.StringRun Code Online (Sandbox Code Playgroud)Stream<String[]> fruityStream = Stream.of(fruits); ^---------------^
我用Google搜索并搜索了但是我什么也没得到.在我看来,这不是一个非常不寻常的或esoeteric问题,所以有点令人惊讶我没有得到任何答案(或者我没有用正确的关键词搜索).
我最近创建了这个示例代码来说明C++ 11可变参数模板函数的用法.
template <typename Head, typename... Tail> void foo (Head, Tail...);
template <typename... Tail> void foo (int, Tail...);
void foo () {}
template <typename... Tail>
void foo (int x, Tail... tail)
{
std :: cout << "int:" << x;
foo (tail...);
}
template <typename Head, typename... Tail>
void foo (Head x, Tail... tail)
{
std :: cout << " ?:" << x;
foo (tail...);
}
foo (int (123), float (123)); // Prints "int:123 ?:123.0"
Run Code Online (Sandbox Code Playgroud)
如果foo省略了前向声明的前两行,则会打印出来int:123int:123.这让一位经验丰富,知识渊博的C++程序员感到惊讶.
他确信前向声明不应该是必要的,因为在两阶段查找的第二阶段之前,身体不会被实例化.他认为编译器(gcc …
c++ variadic-functions one-definition-rule variadic-templates c++11
我们的Java项目中有一个类LogManager,如下所示:
public class LogManager {
public void log(Level logLevel, Object... args) {
// do something
}
public void log(Level logLevel, int value, Object... args) {
// do something else
}
}
Run Code Online (Sandbox Code Playgroud)
在Debian下用OpenJDK 6编译项目时,每个工作都很好.使用OpenJDK 7时,构建(使用ant完成)会产生以下错误,并且构建失败:
[javac] /…/LogManager.java:123: error: reference to log is ambiguous,
both method log(Level,Object...) in LogManager
and method log(Level,int,Object...) in LogManager match
[javac] log(logLevel, 1, logMessage);
[javac] ^
[javac] /…/SomeOtherClass.java:123: error: reference to log is ambiguous,
both method log(Level,Object...) in LogManager
and method log(Level,int,Object...) in …Run Code Online (Sandbox Code Playgroud) java compiler-construction autoboxing overloading variadic-functions
我想知道是否有一种简单,优雅和可重用的方法将字符串和字符串数组传递给期望varargs的方法.
/**
* The entry point with a clearly separated list of parameters.
*/
public void separated(String p1, String ... p2) {
merged(p1, p2, "another string", new String[]{"and", "those", "one"});
}
/**
* For instance, this method outputs all the parameters.
*/
public void merged(String ... p) {
// magic trick
}
Run Code Online (Sandbox Code Playgroud)
即使所有类型都是一致的(String)我也找不到告诉JVM 压扁 p2并将其注入合并参数列表的方法?
此时,唯一的方法是创建一个新数组,将所有内容复制到其中并将其传递给该函数.
任何的想法?
根据您的建议,这里是我将使用的通用方法:
/**
* Merge the T and T[] parameters into a new array.
*
* @param type the …Run Code Online (Sandbox Code Playgroud) 可变参数模板有很多优点,但有时候<cstdarg>应该使用C风格的可变参数函数(使用)吗?
c++ ×3
c++11 ×3
java ×3
c ×2
abi ×1
arrays ×1
autoboxing ×1
constructor ×1
java-8 ×1
java-stream ×1
linux ×1
overloading ×1
ruby ×1
scala ×1
templates ×1
types ×1
x86-64 ×1