我目前正在https://wiki.gnome.org/Projects/Vala/Tutorial处理Vala教程。现在我偶然发现了一个我需要进一步解释的部分;在最后的对象属性部分,本教程介绍了struct属性。举例说明了如何检索这样的属性:
struct Color
{
public uint32 argb;
public Color() { argb = 0x12345678; }
}
class Shape: GLib.Object
{
public Color c { get; set; default = Color(); }
}
int main()
{
Color? c = null;
Shape s = new Shape();
s.get("c", out c);
}
本教程指出:“这样,c
是一个引用而不是堆栈上的Color实例。您传入s.get()
的内容是Color **
而不是Color *.
“
我的问题是关于上述陈述。首先,有人可以详细说明“你传入s.get()
的内容是Color **
而不是Color *.
”的意思。此外,这是否意味着以下
int main()
{
Shape s = new Shape();
Color c = s.c;
}
导致s.c
的{em>值被分配到c
?
编辑:我在valac -C structs.vala
中运行了上述示例。 main
方法的相关C等价物是
gint _vala_main (void) {
gint result = 0;
Color* c = NULL;
Shape* s = NULL;
Shape* _tmp0_ = NULL;
c = NULL;
_tmp0_ = shape_new ();
s = _tmp0_;
g_object_get ((GObject*) s, "c", &c, NULL);
result = 0;
_g_object_unref0 (s);
_color_free0 (c);
return result;
}
答案 0 :(得分:1)
valac
将Vala代码编译成C代码,然后由C编译器(通常是GCC)编译为目标格式(例如目标文件,库或可执行文件)。
所以教程在说Color**
时所说的是生成的C代码将pointer to a pointer to a Color struct
传递给函数(在生成的C代码中为gobject_get
)。
结构是C和Vala *中的值类型,这意味着它们的所有内存都在赋值时被复制。 Vala中的Color?
(nullable Color
)相当于C中的Color*
(a pointer to Color
)。
Vala也会将ref
和out
参数转换为C中的指针,因此在调用pointer to a pointer
或{{1}时会得到双指针(out
)带有可为空的struct变量的参数。
C的输入强度低于Vala,这是很多Vala结构最终成为C中指针的原因.C使用指向状态可选事物的指针,引用,引用调用参数,数组/字符串,链表和其他一些比较模糊的东西(比如函数指针和泛型)。
关于你的第二个问题:直接分配给结构变量时,将会制作一份副本。
* See this question with a great answer by AlThomas解释了在Vala和C级别进行复制的时间。