打开APP
userphoto
未登录

开通VIP,畅享免费电子书等14项超值服

开通VIP
脚本系统:TCC和V8的简单对比
项目中使用V8做为脚本系统,运行速度基本能满足需要,但是有两点问题不太好处理:
一、C++到JS的相互调用及数据类型转换有一定的性能损失
二、GC时的stop-the-world中断时间
这两点基本是无解的。而且发现在最新的V8中,GC的时间不降反升,于是尝试了一下TCC,希望能解决部分问题。

对比方式是用一个简单的相加函数,在脚本中实现,在宿主中调用。

Java代码  
  1. #include <iostream>  
  2. #include <v8.h>  
  3. #include <dew_utils.h>  
  4.   
  5. using namespace v8;  
  6.   
  7. int main(int argc, char** argv)  
  8. {  
  9.     HandleScope scope;  
  10.     Persistent<Context> context=Context::New();  
  11.     Context::Scope context_sceop(context);  
  12.   
  13.     Handle<String> source=String::New("function fun1(a, b) { return a+b; }");  
  14.     Handle<Script> script=Script::Compile(source);  
  15.     script->Run();  
  16.   
  17.     Local<Value> value=context->Global()->Get(String::New("fun1"));  
  18.     if(value->IsFunction())  
  19.     {  
  20.         Local<Function> fun=Local<Function>::Cast(value);  
  21.   
  22.         uint64 t1=GameUtils::msTimeStamp();  
  23.   
  24.         for(int i=0; i<100000; ++i)  
  25.         {  
  26.             Handle<Value> argv[2];  
  27.             argv[0]=Integer::New(5);  
  28.             argv[1]=Integer::New(6);  
  29.   
  30.             Local<Value> result=fun->Call(context->Global(), 2, argv);  
  31.         }  
  32.   
  33.         uint64 t2=GameUtils::msTimeStamp();  
  34.         std::cout<<"Result : "<<int(t2-t1)<<std::endl;  
  35.     }  
  36.   
  37.     context.Dispose();  
  38.     return 0;  
  39. }  


Java代码  
  1. #include <iostream>  
  2. #include <dew_utils.h>  
  3. #include <stdlib.h>  
  4. #include <iostream>  
  5. #include <dew_utils.h>  
  6. #include <stdlib.h>  
  7. #include <stdio.h>  
  8. #include <libtcc.h>  
  9.   
  10. typedef int (*FunType)(intint);  
  11.   
  12. int main(int argc, char** argv)  
  13. {  
  14.     char script[]="void main(int argc, char** argv){} \n int fun1() { return 101; } \n int fun2(int a, int b) { return a+b; }";  
  15.   
  16.     TCCState *s;  
  17.     s=tcc_new();  
  18.     tcc_set_lib_path(s, "/data/lib/tcc-0.9.26");  
  19.     tcc_set_output_type(s, TCC_OUTPUT_MEMORY);  
  20.     tcc_compile_string(s, script);  
  21.     int size=tcc_relocate(s, NULL);  
  22.     void* mem=malloc(size);  
  23.     tcc_relocate(s, mem);  
  24.   
  25.     void* val=tcc_get_symbol(s, "fun1");  
  26.     std::cout<<"Val : "<<*((int*)val)<<std::endl;  
  27.   
  28.     FunType fun=(FunType)tcc_get_symbol(s, "fun2");  
  29.     if(fun)  
  30.     {  
  31.         uint64 t1=GameUtils::msTimeStamp();  
  32.   
  33.         for(int i=0; i<10000000; ++i)  
  34.         {  
  35.             int a=5, b=6;  
  36.             int result=fun(a, b);  
  37.         }  
  38.   
  39.         uint64 t2=GameUtils::msTimeStamp();  
  40.   
  41.         std::cout<<"Result : "<<int(t2-t1)<<std::endl;  
  42.     }  
  43.   
  44.     return 0;  
  45. }  


两种脚本系统中运行时间同为65ms左右,但使用TCC比使用V8的次数多了100倍。这和V8和C++之间相互调用性能不高有很大的关系,同为JIT,相信如果把循环体放在脚本中,差距没有这么严重。

结论:在性能要求比较高的地方,可以考虑用TCC代替V8,以改善本文开始时提到的两点问题。
本站仅提供存储服务,所有内容均由用户发布,如发现有害或侵权内容,请点击举报
打开APP,阅读全文并永久保存 查看更多类似文章
猜你喜欢
类似文章
【热】打开小程序,算一算2024你的财运
TCC(Tiny C Compiler)用C语言当脚本例子
QT笔记66:使用QTUiLoader动态载入控件
使用tcc编译器
C指针函数与函数指针
简要说明C语言中指针函数与函数指针的区别
c 中lambda表达式用法
更多类似文章 >>
生活服务
热点新闻
分享 收藏 导长图 关注 下载文章
绑定账号成功
后续可登录账号畅享VIP特权!
如果VIP功能使用有故障,
可点击这里联系客服!

联系客服