当前位置: 首页 > news >正文

管理网站网络宣传的方法渠道

管理网站,网络宣传的方法渠道,教育局网站建设管理工作意见,百度官方免费下载安装7、Component组件认知与实践 前言 本文是对Cyber RT的学习记录,文章可能存在不严谨、不完善、有缺漏的部分#xff0c;还请大家多多指出。 课程地址: https://apollo.baidu.com/community/course/outline/329?activeId10200 更多还请参考: [1] Apollo星火计划学习笔记——第… 7、Component组件认知与实践 前言 本文是对Cyber RT的学习记录,文章可能存在不严谨、不完善、有缺漏的部分还请大家多多指出。 课程地址: https://apollo.baidu.com/community/course/outline/329?activeId10200 更多还请参考: [1] Apollo星火计划学习笔记——第三讲Apollo Cyber RT 模块详解与实战https://blog.csdn.net/sinat_52032317/article/details/126924375 [2] 【Apollo星火计划】—— Cyber基础概念|通信机制 https://blog.csdn.net/sinat_52032317/article/details/131878429?spm1001.2014.3001.5501 [3] 第一章Cyber RT基础入门与实践https://apollo.baidu.com/community/article/1093 [4] 第二章Cyber RT通信机制解析与实践https://apollo.baidu.com/community/article/1094 [5] 第三章Component组件认知与实践https://apollo.baidu.com/community/article/1103 说明 本文1-4节以此文中的example-component例子为基础 TEST1.Component案例和TEST2.TimerComponent案例基于星火计划中的例子 7.0.前置知识 这部分内容详见第三章Component组件认知与实践https://apollo.baidu.com/community/article/1103 7.0.1 Component定义 Apollo 的 Cyber RT 框架是基于组件(component)概念来构建的。每个组件都是 Cyber RT 框架的一个特定的算法模块 处理一组输入并产生其输出数椐配合Component对应的DAG文件Cyber RT可实现对该模块的动态加载。 7.0.2 Component的类型 Component可分为两类 以消息驱动的Component即只有消息到来时才会调用proc 定时调用的TimerComponent定时调度模块没有绑定消息收发需要用户自己创建reader来读取消息如果需要读取多个消息则可以创建多个reader 注意 Component提供消息融合机制最多可以支持4路消息当从多个channel读取数据的时候以第一个Channel为主Channel当主Channel有消息到达Cyber RT会调用Component的Proc()进行一次数据处理。 TimerComponent不提供消息融合与Component不同的是TimerComponent的Proc()函数不是基于主Channel触发执行而是由系统定时调用开发者可以在配置文件中确定调用的时间间隔。 7.0.3 Component的创建及工作流程 1包含头文件具体见2.1 2定义一个类并继承Component或者timer Component根据component功能需要选择继承Component或者继承TimerComponent 3重写Init()和Proc()函数init函数在Component被加载的时候执行用来对Component进行初始化如Node的创建Node Reader创建Node Writer创建等Proc函数是实现该Component功能的核心函数其中实现了该Component的核心逻辑功能。 4在Cyber Rt中注册该Component只有在Cyber RT中注册了该ComponentCyber RT才能对其进行动态的加载否则报错 7.0.4 Component如何被加载 在Cyber RT中所有的Component都会被编译成独立的.so文件Cyber Rt会根据开发者提供的配置文件按照需要加载对应的Component。所以开发者需要为.so文件编写好配置文件.dag文件和.launch文件以供Cyber RT正确的加载执行Component。 Cyber RT提供两种加载启动Component的方式 使用cyber_launch工具启动Component对应的launch文件 使用mainboard启动component对应的dag文件cyber_launch工具可以启动dag文件和二进制文件而mainboard执行启动dag文件 7.0.5 Component的优点 优点 可以通过配置launch文件加载到不同进程中可以弹性部署可以通过配置DAG文件来修改其中的参数配置调度策略Channel名称可以接收多个种类的消息并有多种消息融合策略接口简单并且可以被Cyber框架动态的加载要创建并启动一个算法组件需要通过以下4个步骤 初始化组件的目录结构实现组件类设置配置文件启动组件7.1.初始化组件的目录结构 ├── BUILD ├── cyberfile.xml ├── example-components.BUILD ├── example.dag ├── example.launch ├── proto │ ├── BUILD │ └── examples.proto └── src ├── BUILD ├── common_component_example.cc ├── common_component_example.h ├── timer_common_component_example.cc └── timer_common_component_example.h C头文件: common_component_example.hC源文件: common_component_example.ccBazel 构建文件: BUILDDAG 文件: examples.dagLaunch 文件: examples.launch7.2.实现组件类 7.2.1 头文件 实现common_component_example.h有以下步骤 包含头文件 基于模板类Component派生出组件类ComponentSample 在派生类中定义自己的Init和proc函数。Proc函数需要指定输入的数据类型 使用CYBER_REGISTER_COMPONENT宏定义把组件类注册成全局可用实例如下所示 #pragma once #include memory#include cyber/component/component.h #include example_components/proto/examples.pb.h// CommonComponentSample类不能被继承 class CommonComponentSample : public apollo::cyber::Componentexample::proto::Driver, example::proto::Driver {//有几个数据就有几个example::proto::Driverpublic:bool Init() override;bool Proc(const std::shared_ptrexample::proto::Driver msg0,const std::shared_ptrexample::proto::Driver msg1) override; }; CYBER_REGISTER_COMPONENT(CommonComponentSample) 模板类Component的定义在cyber/component/component.h中如下所示 template typename M0 NullType, typename M1 NullType,typename M2 NullType, typename M3 NullType class Component : public ComponentBase {public:Component() {}~Component() override {}/*** brief init the component by protobuf object.** param config which is defined in cyber/proto/component_conf.proto** return returns true if successful, otherwise returns false*/bool Initialize(const ComponentConfig config) override;bool Process(const std::shared_ptrM0 msg0, const std::shared_ptrM1 msg1,const std::shared_ptrM2 msg2,const std::shared_ptrM3 msg3);private:/*** brief The process logical of yours.** param msg0 the first channel message.* param msg1 the second channel message.* param msg2 the third channel message.* param msg3 the fourth channel message.** return returns true if successful, otherwise returns false*/virtual bool Proc(const std::shared_ptrM0 msg0,const std::shared_ptrM1 msg1,const std::shared_ptrM2 msg2,const std::shared_ptrM3 msg3) 0; }; 由代码可见Component类最多可以接收4个模板参数每个模板参数均表示一种输入的消息类型这些消息在Proc函数中被周期性的调用和处理 7.2.2 源文件 对于源文件commoncomponent_example.ccInit和Proc这两个函数需要实现。 #include example_components/src/common_component_example.hbool CommonComponentSample::Init() {AINFO Commontest component init;return true; }bool CommonComponentSample::Proc(const std::shared_ptrexample::proto::Driver msg0,const std::shared_ptrexample::proto::Driver msg1) {AINFO Start common component Proc [ msg0-msg_id() ] [ msg1-msg_id() ];return true; } 7.2.3 创建组件源码及BUILD文件bazel编译文件 可见基于common_component_example_lib库最终生成了一个共享库文件libcommon_component_example.so,而该共享库通过Cyber RT调度程序mainboard动态加载运行。 load(//tools:cpplint.bzl, cpplint) load(rules_cc//cc:defs.bzl, cc_binary, cc_library)package(default_visibility [//visibility:public])cc_binary(name libcomponent_examples.so,linkshared True,linkstatic True,deps [:timer_common_component_example_lib,:common_component_example_lib], )cc_library(name timer_common_component_example_lib,srcs [timer_common_component_example.cc],hdrs [timer_common_component_example.h],visibility [//visibility:private],alwayslink True,deps [//cyber,//example_components/proto:examples_cc_proto,], )cc_library(name common_component_example_lib,srcs [common_component_example.cc],hdrs [common_component_example.h],visibility [//visibility:private],alwayslink True,deps [//cyber,//example_components/proto:examples_cc_proto,], )cpplint()7.3.设置配置文件 7.3.1 配置DAG文件 DAG配置文件是Cyber RT调度程序mainboard动态加载模块的最终配置文件。在DAG依赖配置文件例如example.dag中配置如下项目 Channel names: 输入 Channel 的名称Library path: 该组件生成的共享库路径Class name: 此组件类的名称配置实例如下所示 # Define all coms in DAG streaming.module_config { # 共享库文件路径module_library : /opt/apollo/neo/packages/example-components-dev/latest/lib/libcomponent_examples.sotimer_components {class_name : TimerCommonComponentSampleconfig {name : CommonComponent# 消息频率:10msinterval : 10}}components {# 组件类名称一定不能写错否则mainboard无法动态创建CommonComponentSample组件对象class_name : CommonComponentSampleconfig {# 模块名name : examplereaders {channel: /apollo/channel_example/driver_test}readers {channel: /apollo/channel_example/driver_test2}}}}7.3.2 配置Launch启动文件 在launch启动文件中example.launch配置下面的选项 name 组件的名字dag_conf 上一步配置的 DAG 文件路径process_name 运行组件时的进程名配置实例 cybercomponentnamecommon/namedag_conf/apollo/cyber/examples/common_component_example/common.dag/dag_confprocess_namecommon/process_name/component /cyber 7.4.启动组件 通过下面的命令来编译组件 buildtool build --packages example_components运行组件的命令 1通过launch文件启动 cyber_launch start example_components/example.launch2通过.dag文件启动 mainboard -d example_components/example.dag同时在另一个终端开启Cyber_monitor cyber_monitor7.5.TEST1.Component案例 本节实现一个简单的Component实例实现两路channel消息融合并将两路channel消息编号依次打印到屏幕终端。 7.5.1 创建目录结构 apollo_workspace |--test|--common_component_example| |--BUILD // bazel编译文件| |--driver_writer.cc // 向driver channel中写消息的writer| |--chatter_writer.cc // 向chatter channel中写消息的writer| |--common_component_example.cc // component 源文件| |--common_component_example.h // component 头文件| |--common.dag // component 配置文件| |--common.launch // component launch文件|--proto|--BUILD // protobuf的编译文件|--examples.proto // protobuf|--BUILD|--test.BUILD|--cyberfile.xml7.5.2 proto文件及BUILD文件 proto文件 syntax proto2; // proto版本package apollo.cyber.test.proto; // proto命名空间message Chatter {optional uint64 timestamp 1;optional uint64 lidar_timestamp 2;optional uint64 seq 3;optional bytes content 4; };message Driver {optional string content 1;optional uint64 msg_id 2;optional uint64 timestamp 3; };BUILD文件 load(rules_proto//proto:defs.bzl, proto_library) load(rules_cc//cc:defs.bzl, cc_proto_library) load(//tools:python_rules.bzl, py_proto_library)package(default_visibility [//visibility:public])cc_proto_library(name examples_cc_proto,deps [:examples_proto,], )proto_library(name examples_proto,srcs [examples.proto], ) load(rules_proto//proto:defs.bzl, proto_library) proto相关编译规则 load(rules_cc//cc:defs.bzl, cc_proto_library) c相关编译规则 load(//tools:python_rules.bzl, py_proto_library) python相关编译规则,apollo中自定义的7.5.3 driver/chatter writer的实现 chatter_writer.cc #include cyber/cyber.h #include test/common_component_example/proto/examples.pb.h //自己的路径 #include cyber/time/rate.h #include cyber/time/time.husing apollo::cyber::Rate; using apollo::cyber::Time; using apollo::cyber::test::proto::Chatter; //命名空间int main(int argc, char *argv[]) {apollo::cyber::Init(argv[0]);auto talker_node apollo::cyber::CreateNode(chatter_writer);// 创建writer写Chatter类型消息auto talker talker_node-CreateWriterChatter(/apollo/chatter);// 创建计时器Rate rate(3.0);std::string content(apollo_prediction);while (apollo::cyber::OK()) {static uint64_t seq 0;auto msg std::make_sharedChatter(); // Chatter的智能指针msg-set_timestamp(Time::Now().ToNanosecond()); // 时间戳msg-set_lidar_timestamp(Time::Now().ToNanosecond());msg-set_seq(seq);msg-set_content(content std::to_string(seq - 1));talker-Write(msg); // 将数据写入channelAINFO /apollo/chatter sent message, seq (seq - 1) ;;// 每秒3次rate.Sleep();}return 0; } driver_writer.cc #include cyber/cyber.h #include test/common_component_example/proto/examples.pb.h #include cyber/time/rate.h #include cyber/time/time.husing apollo::cyber::Rate; using apollo::cyber::Time; using apollo::cyber::test::proto::Driver;int main(int argc, char *argv[]) {// 初始化cyberapollo::cyber::Init(argv[0]);// 创建nodeauto talker_node apollo::cyber::CreateNode(driver_writer);// 创建writer写Driver类型消息auto talker talker_node-CreateWriterDriver(/apollo/driver);// 新建计时器Rate rate(2.0);std::string content(apollo_test);while (apollo::cyber::OK()) {static uint64_t seq 0;auto msg std::make_sharedDriver();// 创建一个Driver类型的消息并填入数据msg-set_timestamp(Time::Now().ToNanosecond());msg-set_msg_id(seq);msg-set_content(content std::to_string(seq - 1));talker-Write(msg);AINFO /apollo/driver sent message, seq (seq - 1) ;;// 每秒2次rate.Sleep();}return 0; } 7.5.4 component实现 common_component_example.h #pragma once #include memory#include cyber/component/component.h #include test/common_component_example/proto/examples.pb.husing apollo::cyber::Component; using apollo::cyber::ComponentBase; using apollo::cyber::test::proto::Driver; using apollo::cyber::test::proto::Chatter;// 有两个消息源继承以Driver和Chatter为参数的Component模版类 class CommonComponentSample : public ComponentDriver, Chatter {public:bool Init() override;// Proc() 函数的两个参数表示两个channel中的最新的信息bool Proc(const std::shared_ptrDriver msg0,const std::shared_ptrChatter msg1) override; }; // 将CommonComopnentSample注册在cyber中 CYBER_REGISTER_COMPONENT(CommonComponentSample) 可以看到此处继承了ComponentDriver, Chatter来读取两个 channel 中的两种格式的消息Proc()函数参数与其相对应。以此类推如果继承了ComponentDriver, Chatter, Driver则Proc()函数应为 Proc(const std::shared_ptr msg0, const std::shared_ptr msg1, const std::shared_ptr msg2) common_component_example.cc #include test/common_component_example/com_component_test/common_component_example.h // 在加载component时调用 bool CommonComponentSample::Init() {AINFO Commontest component init;return true; } // 在主channel也就是Driver有消息到达时调用 bool CommonComponentSample::Proc(const std::shared_ptrDriver msg0,const std::shared_ptrChatter msg1) {// 将两个消息的序号格式化输出AINFO Start common component Proc [ msg0-msg_id() ] [ msg1-seq() ];return true; } 7.5.5 配置文件 DAG文件 module_config {module_library : /opt/apollo/neo/packages/test-dev/latest/lib/libcommon_component_example.socomponents {class_name : CommonComponentSampleconfig {name : commonreaders {channel: /apollo/driver}readers {channel: /apollo/chatter}}}}module_library指向 Component 编译后得到的.so文件的存放目录。components表示 Component 的类型除了components外还有一种是timer_component将会在下个例子中讲解。class_name表示被加载的 Component 的类名在这个例子中是 CommonComponentSample。name表示被加载的类在 Cyber 中的标识名。readers表示 Component 所读取的 Channel 与其继承的基类读取的类型一一对应。launch文件 cybermodulenamecommon/namedag_conf/apollo_workspace/test/common_component_example/com_component_test/common.dag/dag_confprocess_namecommon/process_name/module /cyber name表示加载的 Component 在 Cyber 中的标识名与 dag 文件中的name字段对应。 dag_conf表示 dag 配置文件路径。 process_name表示启动后的线程名与线程名相同的component 会在此线程中运行。BUILD文件-bazel编译文件 load(rules_cc//cc:defs.bzl, cc_binary, cc_library) load(//tools/install:install.bzl, install, install_src_files) load(//tools:cpplint.bzl, cpplint)package(default_visibility [//visibility:public])cc_binary(name libcommon_component_example.so,linkshared True,linkstatic True,deps [:common_component_example_lib], )cc_library(name common_component_example_lib,srcs [common_component_example.cc],hdrs [common_component_example.h],visibility [//visibility:private],deps [//cyber,//test/common_component_example/proto:examples_cc_proto, // 路径按自己的改],alwayslink True, )cc_binary(name driver_writer,srcs [driver_writer.cc],linkstatic True,deps [//cyber,//test/common_component_example/proto:examples_cc_proto,], )cc_binary(name chatter_writer,srcs [chatter_writer.cc],linkstatic True,deps [//cyber,//test/common_component_example/proto:examples_cc_proto,], )filegroup(name conf,srcs [:common.dag,:common.launch,], )install(name install,data [:conf,],runtime_dest test/bin,library_dest test/lib,data_dest test/common_component_example/conf,targets [:chatter_writer,:driver_writer,libcommon_component_example.so,], )install_src_files(name install_src,src_dir [.],dest test/src/common_component_example,filter *, )cpplint() 编译 buildtool build -p test/注意 install关键字 runtime_dest 可执行文件位置library_dest 库文件位置data_dest.dag/.launch 文件的位置记得修改包管理BUILD文件中的deps 运行 完成编译后我们就可以运行 Cyber 并加载 Component了如上文所说Cyber 会根据配置文件来加载 Component。Cyber 提供了两种加载 Component 的方法 方法一、使用mainboard启动mainboard -d path/to/dag在这个例子中运行的命令是 mainboard -d test/common_component_example/common.dag方法二、使用cyber_launch启动cyber_launch start path/to/launch在这个例子中运行的命令是 cyber_launch start test/common_component/common.launch启动三个终端 #第一个 export GLOG_alsologtostderr1 ./bazel-bin/test/common_component_example/driver_writer#第二个 export GLOG_alsologtostderr1 ./bazel-bin/test/common_component_example/chatter_writer#第三个 export GLOG_alsologtostderr1 cyber_launch start test/common_component_example/common.launchcyber_monitor可以查看channel信息 CommonComponentSample每接受到一次主channel信息执行一次Proc()函数,Proc()函数执行消息融合逻辑依次打印出两路消息的编号到屏幕上。 可以看到CommonComponentSample打印到屏幕上的信息其中主channel信息Driver信息编号是依次递增的而非主channel信息Chatter信息编号会出现缺失或者重复这是因为component的Proc()函数只有主channel消息到达时才会触发执行Proc()函数执行时会读取所有融合channel最新消息。 6.TEST2.TimerComponent案例 在本节中我们会实现两个TimerComponent分别是TimerDriverSample和TimerChatterSample用来替换掉上一个案例中的两个 Writer。 7.6.1 创建目录结构 apollo_workspace |--test|--timer_component_example|--BUILD|--timer_chatter.h // TimerChatterSample 头文件|--timer_chatter.cc // TimerChatterSample 源文件|--timer_driver.h // TimerDriverSample 头文件|--timer_driver.cc // TimerDriverSample 源文件|--driver.dag // TimerDriverSample 配置文件|--driver.launch // TimerDriverSample launch文件|--chatter.dag // TimerChatterSample 配置文件|--chatter.launch // TimerChatterSample launch文件 7.6.2 proto文件及BUILD文件 沿用TEST1中的文件 7.6.3TimerComponent 实现 timer_chatter.h #include memory #include cyber/class_loader/class_loader.h #include cyber/component/component.h #include cyber/component/timer_component.h #include test/common_component_example/proto/examples.pb.husing apollo::cyber::Component; using apollo::cyber::ComponentBase; using apollo::cyber::TimerComponent; using apollo::cyber::Writer; using apollo::cyber::test::proto::Chatter;class TimerChatterSample : public TimerComponent {public:bool Init() override;bool Proc() override;private:std::shared_ptrWriterChatter chatter_writer_ nullptr; }; CYBER_REGISTER_COMPONENT(TimerChatterSample)可以看到TimeChatterComponent 需要继承 TimerComponent基类代码结构与普通的 Component 几乎相同。 不同的是因为没有数据源所以没有模版参数。timer_chatter.cc #include test/timer_component_example/timer_chatter.h #include cyber/class_loader/class_loader.h #include cyber/component/component.h #include test/common_component_example/proto/examples.pb.hbool TimerChatterSample::Init() {chatter_writer_ node_-CreateWriterChatter(/apollo/chatter);return true; }bool TimerChatterSample::Proc() {static int i 0;auto out_msg std::make_sharedChatter();out_msg-set_seq(i);chatter_writer_-Write(out_msg);AINFO timer_chatter: Write chattermsg- out_msg-ShortDebugString();return true; }TimerChatter 在 Init()中初始化了 Writer并在 Proc()中向 Channel 中写信息。 timer_driver.h #include memory #include cyber/class_loader/class_loader.h #include cyber/component/component.h #include cyber/component/timer_component.h #include test/common_component_example/proto/examples.pb.husing apollo::cyber::Component; using apollo::cyber::ComponentBase; using apollo::cyber::TimerComponent; using apollo::cyber::Writer; using apollo::cyber::test::proto::Driver;class TimerDriverSample : public TimerComponent {public:bool Init() override;bool Proc() override;private:std::shared_ptrWriterDriver driver_writer_ nullptr; }; CYBER_REGISTER_COMPONENT(TimerDriverSample)timer_driver.cc #include test/timer_component_example/timer_driver.h #include cyber/class_loader/class_loader.h #include cyber/component/component.h #include test/common_component_example/proto/examples.pb.h bool TimerDriverSample::Init() {driver_writer_ node_-CreateWriterDriver(/apollo/driver);return true; }bool TimerDriverSample::Proc() {static int i 0;auto out_msg std::make_sharedDriver();out_msg-set_msg_id(i);driver_writer_-Write(out_msg);AINFO timer_driver: Write drivermsg- out_msg-ShortDebugString();return true; }7.6.4 配置文件 chatter.dag module_config {module_library : /opt/apollo/neo/packages/test-dev/latest/lib/libtimer_chatter.sotimer_components {class_name : TimerChatterSampleconfig {name : timer_chatterinterval : 400}} }interval表示 TimerComponent 执行 Proc()的间隔此配置中为 400 ms 执行一次。 因为没有数据融合所以没有readers字段 其余配置和普通 Component 相同chatter.launch cybermodulenametimer_chatter/namedag_conf/opt/apollo/neo/packages/test-dev/latest/timer_component_example/conf/chatter.dag/dag_confprocess_nametimer_chatter/process_name/module /cyberdriver.dag module_config {module_library : /opt/apollo/neo/packages/test-dev/latest/lib/libtimer_driver.sotimer_components {class_name : TimerDriverSampleconfig {name : timer_driverinterval : 200}} }driver.launch cybermodulenametimer_driver/namedag_conf/opt/apollo/neo/packages/test-dev/latest/timer_component_example/conf/driver.dag/dag_confprocess_nametimer_driver/process_name/module /cyber7.6.5 BUILD文件 load(rules_cc//cc:defs.bzl, cc_binary, cc_library) load(//tools/install:install.bzl, install, install_src_files) load(//tools:cpplint.bzl, cpplint)package(default_visibility [//visibility:public])cc_binary(name libcommon_component_example.so,linkshared True,linkstatic True,deps [:common_component_example_lib], )cc_library(name common_component_example_lib,srcs [common_component_example.cc],hdrs [common_component_example.h],visibility [//visibility:private],deps [//cyber,//test/common_component_example/proto:examples_cc_proto,],alwayslink True, )cc_binary(name driver_writer,srcs [driver_writer.cc],linkstatic True,deps [//cyber,//test/common_component_example/proto:examples_cc_proto,], )cc_binary(name chatter_writer,srcs [chatter_writer.cc],linkstatic True,deps [//cyber,//test/common_component_example/proto:examples_cc_proto,], )filegroup(name conf,srcs [:common.dag,:common.launch,], )install(name install,data [:conf,],runtime_dest test/bin,library_dest test/lib,data_dest test/common_component_example/conf,targets [:chatter_writer,:driver_writer,libcommon_component_example.so,], )install_src_files(name install_src,src_dir [.],dest test/src/cyberatest,filter *, )cpplint()记得修改包管理BUILD文件中的deps. 7.6.6 编译运行 编译 同上 运行 我们实现的两个 TimerComponent 可以用来替代上一个案例中的两个定时写消息的 Writer启动方法也与上一案例类似不同的是 TimerComponent 可以通过配置文件配置。 同样开启三个终端 # 第一个 export GLOG_alsologtostderr1 cyber_launch start test/common_component_example/common.launch# 第二个 export GLOG_alsologtostderr1 cyber_launch start test/timer_component_example/driver.launch# 第三个 export GLOG_alsologtostderr1 cyber_launch start test/timer_component_example/chatter.launchCommonComponentSample每接受到一次主channel信息执行一次Proc()函数,Proc()函数执行消息融合逻辑依次打印出两路消息的编号到屏幕上。 TimerChatterSample每隔400ms/200ms由系统定时器调用Proc()函数Proc()函数每执行一次就发出一条消息。并打印该条消息的编号到屏幕上。
http://wiki.neutronadmin.com/news/49892/

相关文章:

  • 网站建站公司哪家好浙江公铁建设工程有限公司网站
  • 做网站公司能赚钱吗网站怎么修改模板内容
  • 世纪佳缘网站模板网站建设专有名词
  • 手机网站推荐大全网络销售工作怎么样
  • 做网站后都需要什么android studio官网下载
  • 网站开发需要哪些职位网站建设预算明细表
  • 网站建设的基本流程可分为签证中心网站建设
  • 银川网站建设广告公司wordpress 安装ssl
  • 打造自己的网站南川区 网站集约化建设方案
  • 学校网站空间建设情况wordpress直播购物插件
  • 深圳做网站(信科网络)网站友情链接模板
  • 如何设置中国建设银行网站外贸平台有哪些国际
  • 商业网站建设设计郑州网站设计收费
  • 合肥公司网站建设价格上海做网站哪家公司好
  • 学校网站建设文字规范问题工商注册地址有什么要求
  • 网站权重分为几个等级网站建设的组织机构
  • 手机网站自适应分辨率福州seo顾问
  • 云主机建设网站网站开发简单
  • 站长工具seo综合查询是什么意思网站开发定制案例展示
  • 衡阳做网站的公司网站做轮播图的意义
  • 网站设计手机闵行区属于浦东还是浦西
  • 网站建设管理工作简述wordpress常常被用来做什么网站
  • 企业网站建设太原网站建设wordpress做菜鸟教程
  • 专业建站公司的业务内容有哪些泉州网站建设公司首选公司
  • 网站现状如何分析平台推广怎么写
  • 上蔡做网站毕设做网站什么主题比较好
  • 财经网站源码 织梦网站开发 鲁山
  • 牛杂网这类网站怎么做的数商云网络科技有限公司
  • 张家界简单的网站建设二级医院做网站
  • 网站的动画广告横幅怎么做的优化网站