网普科技
网普管理员
网普科技人民公仆
积分 3080
发贴 2863
注册 2004-6-26 来自 网普科技
状态 离线
|
#11 在你的游戏中应用Lua(3):Using Lua in cpp(基本数据类型、指针和引用)之一
前面介绍的都是针对cpp中的内建基本数据类型,然而,即使是这样,在面对指针和引用的时候,情况也会变得复杂起来。
使用前面我们已经完成的宏lua_register_directclosure只能注册by value形式的参数的函数,当参数中存在指针和引用的时候(再强调一次,目前只针对基本数据类型):
1、 如果是一个指针,通常实现函数的意图是以这个指针传递出一个结果来。
2、 如果是一个引用,同上。
3、 如果是一个const指针,通常只有面对char*的时候才使用const,实现函数的意图是,不会改变这个参数的内容。其它情况一般都避免出现使用const指针。
4、 如果是一个const引用,对于基本数据类型来说,一般都避免出现这种情况。
Lua和cpp都允许函数用某种方式返回多个值,对于cpp来说,多个返回值是通过上述的第1和第2种情况返回的,对于lua来说,多个返回值可以直接返回:
--in Lua
function swap(x, y)
tmp = x
x = y
y = tmp
return x, y
end
x = 100
y = 200
x, y = swap(x, y)
print(x..y)
程序输出:200100
同样的,在主机程序中,我们也可以向Lua返回多个值:
int swap(lua_State *L)
{
//取得两个参数
int x = Get(TypeWrapper<int>(), L, -1);
int y = Get(TypeWrapper<int>(), L, -2);
//交换值
int tmp = x;
x = y;
y = tmp;
//向Lua返回值
Push(L, x);
Push(L, y);
//告诉Lua我们返回了多少个值
return 2;
}
现在我们可以在Lua中这样调用这个函数:
x = 100
y = 200
x, y = swap(x, y)
在我们的register_proxy函数中只能对基本数据类型的by value方式有效,根据我们上面的分析,如果我们能够在编译期知道,对于一个模板参数T:
1、 这是一个基本的数据类型,还是一个用户自定义的数据类型?
2、 这是一个普通的指针,还是一个iterator?
3、 这是一个引用吗?
4、 这是一个const 普通指针吗?
5、 这是一个const 引用吗?
如果我们能知道这些,那么,根据我们上面的分析,我们希望:(只针对基本数据类型)
1、 如果这是一个指针,我们希望把指针所指的内容返回给Lua。
2、 如果这是一个引用,我们希望把引用的指返回给Lua。
3、 如果这是const指针,我们希望将从Lua栈中取得的参数传递给调用函数。
4、 如果这是一个const引用,我们也希望把从Lua栈中取得的参数传递给调用函数。
|
天理路上甚宽,稍游心,胸中便觉广大宏朗;
人欲路上甚窄,才寄迹,眼前俱是荆棘泥涂。
网普科技,优质美国主机服务!
美国Linux主机,美国虚拟主机
支持PHP+MYSQL+cPanel+EMAIL
为用户负责,拒绝反动、赌博及色情内容! QQ:126818
发送QQ消息 |
|
2007-4-6 11:10 AM |
|
网普科技
网普管理员
网普科技人民公仆
积分 3080
发贴 2863
注册 2004-6-26 来自 网普科技
状态 离线
|
#12 在你的游戏中应用Lua(3):Using Lua in cpp(基本数据类型、指针和引用)之二
现在首要的问题在于,我们希望通过某种方式,在编译期获得一个模板参数T是不是一个指针或者一个引用?幸运的是,boost库已经提供了这样的功能,boost提供了一组type_traits,让我们能够在编译期获取模板参数T的类型。
你可以从http://boost.sourceforge.net/index.htm ;下载boost库,我们需要的是boost的type_traits一组头文件。
下载完 boost库之后,并设置好包含路径,让我们开始修改我们的Call函数,对指针和引用做出适当的改变。
有了boost库之后,测试一个模板参数T是指针还是引用再也简单不过了:
#include <boost/type_traits.hpp>
using namespace boost;
template <typename RT, typename P1>
int Call(RT (*Func) (P1), lua_State *L, int idx)
{
is_pointer<P1>::value || is_reference<P1>::value;
}
现在我们已经能够得到一个bool值,如果这个值为真,我们并不试图从lua栈中获取这样的参数,而是首先将它交给调用函数处理,然后再作为返回值交给lua,并且返回的时候,是返回这个指针所指内容的拷贝。如果为假,我们仅仅将它作为参数交给调用函数。
为了能够做到编译期的静态分派,我们使用函数的重载机制,首先,我们需要定义一个bool到类型的映射,以区别参数的类型:
template <bool B>
struct bool2type
{
enum { value = B };
};
为了清晰起见,我们对两种形式做一个typedef:
typedef bool2type<true> ResultType;
typedef bool2type<false> NormalType;
对于一个参数来说,如果它的标志是ResultType,那么它将作为结果交给lua,如果是第二种形式,那么它仅仅交给被调函数。
现在我们要为一个参数的Call函数提供两个版本的_Call函数,以区分其指针参数调用和正常调用:
template <typename RT, typename P1>
int _Call(RT (*Func)(P1), ResultType, lua_State *L, int idx)
{
}
template <typename RT, typename P1>
int _Call(RT (*Func)(P1), NormalType, lua_State *L, int idx)
{
}
现在我们在Call函数中可以直接交给_Call来处理:
template <typenaem RT, typename P1>
int Call(RT(*Func)(P1), lua_State *L, int idx)
{
return _Call(*Func,
bool2type<is_pointer<P1>::value
|| is_reference<P1>::value>(), L, idx);
}
|
天理路上甚宽,稍游心,胸中便觉广大宏朗;
人欲路上甚窄,才寄迹,眼前俱是荆棘泥涂。
网普科技,优质美国主机服务!
美国Linux主机,美国虚拟主机
支持PHP+MYSQL+cPanel+EMAIL
为用户负责,拒绝反动、赌博及色情内容! QQ:126818
发送QQ消息 |
|
2007-4-6 11:11 AM |
|
网普科技
网普管理员
网普科技人民公仆
积分 3080
发贴 2863
注册 2004-6-26 来自 网普科技
状态 离线
|
#13 在你的游戏中应用Lua(4):做为配置语言
任何一种语言的存在都是为了表达,做为一种动态配置的语言,Lua提供给我们非常强大也非常的灵活的表达方式。
Lua 是一种动态类型的语言,它只有几种基本的类型:nil,boolean,number,string,userdata,function,thread 和table。Nil,boolean,number,string这些与其它语言都类似。由于Lua实现了动态内存管理,所以在使用string的时候无须担心内存分配和释放问题。
在Lua中,function就是值,可以被存储在一个变量中,可以做为另一个function的参数,可以做为返回值被返回。
Userdata 表现了一块原始的内存区域,它可以被存储在变量中,在Lua中没有对userdata的预定义操作,除了赋值和相等测试。Userdata不能在Lua中创建和修改,只能通过c api来操作userdata。Userdata表现了一个句柄的概念,你可以在Lua中持有它,可以交给任何c cpi来操作它,但是不能在Lua中改变它。
Thread表现了独立执行的线程,被用来实现coroutines。
Table是Lua中唯一的数据结构,它提供给我们非同寻常的表达能力,在Lua中,你可以用Table来表现一个Array,dynamic array,List,Set,queue,map等等,所有这些都可以使用table,用一种简单的一致的方式来表达。
在Lua中,table既不是值,也不是变量,实际上,它是Lua中的对象,我们不能声明一个Table,只能通过Table的构造器创建一个Table:
A = {}
在Lua中,Table永远都是匿名的,在上面的语句中,我们创建了一个table,然后让变量A引用到这个table,这意味着,在一个引用到一个table的变量和table本身之间没有固定的关系。从下面这个例子可以看出:
A = {}
A.name = “Lua”
B = A
A = nil
print(B.name)
程序将输出”lua”而不是nil
当程序不再用到一个table时,lua内存管理器将自动释放其内存。
|
天理路上甚宽,稍游心,胸中便觉广大宏朗;
人欲路上甚窄,才寄迹,眼前俱是荆棘泥涂。
网普科技,优质美国主机服务!
美国Linux主机,美国虚拟主机
支持PHP+MYSQL+cPanel+EMAIL
为用户负责,拒绝反动、赌博及色情内容! QQ:126818
发送QQ消息 |
|
2007-4-6 11:11 AM |
|
茱莉娅
THE BODY SHOP美容顾问
茱莉娅美体小铺
积分 3080
发贴 2863
注册 2009-5-21
来自 茱莉娅美体小铺
状态 离线
|
|
2007-4-6 11:11 AM |
|
|