标题：unreal script
基本特性
Unreal Script是由Epic Games为了适应游戏编程的自然需要和细微差别而为虚幻系列引擎创建的一种的类C/JAVA语言.
设计目标UnrealScript的主要设计目标是：
支持传统编程语言没有解决的时间，状态，属性的网络化。这大大简化了UnrealScript的代码。编写基于人工智能和游戏逻辑的程序，主要运用事件交互技术，这些事件采取一定的游戏时间完成，并且事件非常依赖对象状态，这让网络化问题极度复杂化。在c/c++中书写、理解、维护和调试这样的代码是非常困难的。UnrealScript天生支持时间、状态、网络复制大大简化了游戏编程。
提供Java编程风格，简单、基于对象的、编译时错误检查的特性。就象Java为Web程序员带来了清晰、简洁的编程平台一样，UnrealScript为3D游戏程序员提供了一个同样清晰、简洁、可靠的编程语言。从Java继承的主要编程概念如下：
具有自动垃圾收集的无指针环境;
一个简单的类单一继承机制;
强壮的编译时类型检查;
安全客户端执行的“沙盒”;
熟悉的c/c++/java代码外观和感受;
提供游戏对象丰富的高层互动，而不是底层的位和像素。在设计权衡时，由于UnrealScript工作在对象互动层，而不是底层的位和像素，因此在UnrealScript中，牺牲了性能选择了简单性和功能。而在底层和性能的关键代码是用c/c++写的，在这些地方增加性能获得的好处超过了增加复杂性得到的坏处，选择了性能牺牲了简单性和功能。
类
概述每个脚本文件对应一个类，以class声明为开头，后面是类的父类和类的相关信息。简单的例子如下：
class MyClass extends MyParentClass;
这里声明了一个名称为“MyClass”的新类，这个类继承了“MyParentClass“的所有功能。此外类驻留在名为”MyPackage“的包中。
每个类继承父类的所有变量和函数以及状态。每个类都可以申明新的变量和新的函数（或者重写已经存在的函数）以及添加新的状态（或为已有的状态添加功能）。
在UnrealScript中设计一个新类（例如一个牛头人怪物）的典型的做法是，从具备你需要的功能的已有类（例如，Pawn类，所有怪物的基类）继承。
通过这样的做法，你永远都不用重新发明轮子--可以简单的添加新功能，你可以在自定义的同时保持不需要定制的现有功能。这种做法特别适合从虚幻中继承AI，内置的AI系统提供了大量的基本功能，同时你还可以建立自己的生物。类关键字Native（包名称）(本机类)
指示：“这个类使用幕后c++支持“。虚幻native类包含在一个c++写的exe中。只有native类可以申明native函数或实现native接口。native始终来自native类。与脚本变量和特定的函数协作，native类需要创建一个自动生成的C ++头文件。默认情况下，包名是脚本类所在的exe名称。例如，引擎包中的类，要求EngineClasses.h文件。
NativeReplication
表示这个类的变量复制处理在c++中实现。只能用于native类。
DependsOn(ClassName[,ClassName,....])（依赖于）
表示ClassName是在这个类前编译。ClassName必须和这个类处于同一个包或者前一个包。可以用一个DependsOn指定多个依赖类，他们用逗号隔开。也可以使用多个DependsOn指定。
Abstract
声明类是一个“基本的抽象类”。这可以防止这个类被无意的实例化。这个关键字会对其内部子类起作用，但是不会对其他脚本文件中的子类起作用。
Deprecated（过时的）
类的所有对象被加载但不保存。当关卡设计师在关卡设计器中载入包含过时活动对象被的地图时，他们会收到编辑器的警告信息。这个关键字会对其子类产生作用。
Transient（瞬态）
表示该类的对象不应该被保存在磁盘上，这和一些非持久性的本机类自然结合是有用的。比如播放器和窗口。这个关键字会对其子类起作用；子类能使用NotTransient关键字重写它。
NotTransient（非瞬态）
表示不从基类继承Transient关键字标注的瞬态特性。
Config(IniName)(配置）
表明这个类允许访问ini文件中的数据。如果在类中有可配置变量（使用config和globalconfig申明），这可以让类访问那些保存在指定的配置文件的变量。这个标志将被传播到所有子类并且不能被否定，但是子类可以通过config关键字指定不同的配置文件。通常IniName指定ini文件的名称去存储数据，但有些名字具有特殊意义：
Config(Engine):用于引擎配置文件，通过你的游戏名称追加"Engine.ini"。例如，ExampleGame游戏的引擎配置文件名称是"ExampleEngine.ini"。
Config(Editor)：用于编辑器配置文件。通过你的游戏名称追加“Editor.ini"。例如，ExampleGame游戏的编辑器配置文件名称是"ExampleEditor.ini"。
Config(Game): 用于游戏配置文件。通过你的游戏名称追加"Game.ini"。例如，ExampleGame游戏的配置文件名称是 ExampleGame.ini。
Config(Input)：用于输入配置文件。通过你的游戏名称追加“Input.ini“。例如，ExampleGame游戏的输入配置文件名称是ExampleInput.ini。
PerObjectConfig：类的每个对象的配置信息都会被保存在配置文件中。每个对象在配置文件中都有一个如下格式的配置节[ObjectName ClassName]。这个关键字会对其子类起作用。
PerObjectLocalized
类得本地化数据将被定义在每对象得基础上。每个对象在已命名得本地化文件中有个如下格式得节[ObjectName ClassName]。这个关键字会对其子类起作用。
EditInlineNew
编辑器，表示这个类的对象能从虚幻便捷器的属性窗口创建（默认行为是可以通过关联的属性窗口引用已经存在的对象）。这个关键字会对其子类起作用。子类可以使用NotEditInlineNew关键字重写它。
NotEditInlineNew
编辑器，不从基类继承EditInlineNew关键字。如果没有任何父类使用EditInlineNew关键字将不起效果。
Placeable(可放置)
编辑器。表示这个类可以通过虚幻编辑器放到关卡，UI场景，或者kismet窗口（由类的类型定）。这个标志将被传播到其所有子类中；子类能通过NotPlaceable关键字重写它。
NotPlaceable
编辑器。不从基类继承NotPlaceable关键字。表示这个类不能在虚幻编辑器中放入关卡。
HideDropDown
编辑器。防止这个类在虚幻编辑器的属性窗口的组合框中显示。
HideCategories(Category[,Gategory,......])
编辑器。表示这个类的对象在虚幻编辑器的属性窗口中隐藏一个或多个类别。使用无类别声明可以隐藏变量，使用类名称声明变量的名称。
ShowCategories(Category[,Category,......])
编辑器。不从基类继承ShowCategories关键字。
AutoExpandCategories(Category[,Category,......])
编辑器。指示一个或多个类别在编辑器的属性窗口中自动展开。使用无类别声明可以自动展开变量，使用类名称声明变量的名称。
Collapsecategories
编辑器。表示类的属性不应该在虚幻编辑器的属性窗口类别中被分组。这个关键字会对其子类起作用；子类可以用DontCollapsecategories关键字重写它。
DontCollapsecategories
编辑器。表示不从基类继承Collapsecategories。
Within ClassName
高级。表示类的对象离不开ClassName的实例。为了建立这个类的对象，您必须指定作为外部对象ClassName的实例。这个关键字必须作为class申明的后的第一关键字。
Inherits(ClassName[,ClassName,......])
高级，使用多继承。只是适用于native类。不支持从多个UObject类继承。
Implements(ClassName[,ClassName,......])(实现)
高级。指示类实现的多个接口。只有nataive类可以实现native接口。
NoExport
高级。表明这个类的c++声明不应该通过脚本编译器包含在自动生成c++头文件中。类的c++声明手动定义在一个单独的头文件中。只适用于native类。
变量
变量类型内置类型 (Built-in types)
这里有一些在 UnrealScript 中宣告变量的例子：
var int a; // 宣告一个名称为"A"的整数变量。
var byte Table[64]; // 宣告一个长度64的静态 1-byte 阵列。
var string PlayerName; // 宣告一个名称为"PlayerName"的字串变量。
var actor Other; // 实体化 Actor 类别，并命名为"Other"。
var() float MaxTargetDist; // 宣告一个名称为"MaxTargetDist"的浮点数变量，并且它的值可以从 UnrealEd 的属性窗口中修改。
变量在 UnrealScript 能出现在两种地方：实体变量，它可以在整个类别内使用，在宣告完类别或 struct 后立即出现。局部变量，出现在函数中，只有在函数执行时有效。实体变量使用关键字 var 宣告。局部变量用关键字 local 宣告，例如：
function int Foo()
{
local int Count;//声明一个整型的局部变量 Count
Count = 1;
return Count;
}
但在声明局部变量的时候,必须在声明全部局部后,才能编写功能函数.
以下是 UnrealScript 中支持的内置变量类型：
byte: 1-byte 值，范围从 0 到 255。
int: 32-bit 整数值。
bool: 布林运算值: 不是 true 就是 false。
float: 32-bit 浮点数值。
string: 一个字串(see Unreal Strings)。
constant: 不能修改的变量。
enumeration: 一个能够代表多个预先设定的整数值中的其中一个值。例如：在 Actor 内定义为 enumeration 的变量ELightType 描述了一个动态光源，它的值可以像 LT_None、LT_Pulse、LT_Strobe，等等...。可编辑性在UnrealScript中，你可以使一个实例变量变得可编辑，以便用户可以在UnrealEd中编辑变量的值。这个机制负责了UnrealEd 的"Actor Properties(Actor属性)"对话框的全部内容： 您在那里所看到的全部内容仅是UnrealScript中的一个声明为可以编辑的变量。 
声明一个可以编辑的变量的语法如下所示：
var() int MyInteger;
var(MyCategory) bool MyBool; 
您也可以声明一个变量为 editconst ，这意味着这个变量将可以在UnrealEd中看见但 不 可以编辑。注意这仅仅是为了防止变量在编辑器中被改变而不是在脚本中。如果您想使一个变量为真正的 const 但是仍然可以在编辑器中可见，您必须声明它为 const editconst ：
var(MyCategory) editconst bool MyBool;
var(MyCategory) const editconst bool MyBool;
var(MyCategory) const bool MyBool;数组数组使用以下语法声明： 
var int MyArray[20];
UnrealScript仅支持一维数组，但你可以通过自己来设置 行/列 的数学处理来模拟多维数组。动态数组为了适应数组元素变化的需要，动态数组提供了一种使静态数组具有在运行时改变元素数量的功能的方法。如果想使用动态数组，我们需要知道几件事情。 
首先是变量的声明。声明一个动态数组和声明其它的unrealscript变量是非常相似的(也就是var/local 类型 变量名 )。 对于动态数组，类型可以使用关键字 array 来指定，后面跟着由尖括号括起的数组类型。 如果数组类型也包含尖括号(比如 class<Actor> )，你必须在类型的结束括号和数组的结束括号之间加入空格，否则编译器会把这两个结束括号作为 >> 操作符来处理。比如：
声明一个叫IntList的动态整型数组:
var array<int> IntList;
声明一个类型为 class<PlayerController> 、名称为Players的动态数组：
var array<class<PlayerController> > Players;
当脚本开始运行时，IntList将从0元素开始。动态数组所支持的方法允许我们向数组中添加元素、取出元素及任意地增加或降低数组的长度。调用这些方法的语法是(使用我们的IntList为例子)： IntList.MethodName() 。以下是动态数组提供的方法：
◆Add(int Count): 通过使用 Count 来扩展数组的长度，和FArray::AddZeroed()一样。
◆Insert(int Index, int Count): Index_是插入元素的索引位置， _Count 是插入的元素数量。任何在那个位置存在的元素将会被上移，将会创建新的元素并把它们插入到指定的位置。在索引为3的位置插入5个元素将会使数组中从索引3 开始的所有元素都会被上移5位。现在放在索引3出的元素将会被放置到索引8，元素4将是元素9等等。* Remove(int Index, int Count):_Index_ 是指从何处开始移除元素的索引， Count 是要移除的元素的数量。 新增加的元素都被初始化为默认值(除了structs包含structdefaultproperties外，其它所有元素将被初始化为 0/空)。 
◆Remove(int Index, int Count): 这里 Index 是从其开始删除元素的数组索引， Count 是要删除的元素的数量。  这允许我们从数组中任何有效的索引开始来移除数组中的一组元素。注意任何高于将被删除的范围的索引将会改变它们的索引值，如果您存储索引值到一个动态数组中时请记住这一点。 
◆AddItem(Item): 在数组的末尾增加一个元素 Item ，从而是数组的长度加1。
◆RemoveItem(Item): 使用线性搜索来删除任何元素实例 Item 。
◆InsertItem(int Index, Item): 将元素 Item 插入到数组中的索引 Index 处，从而是数组的长度加1。
◆Find(...) - 查找一个元素在数组中的索引。有两个Find函数版本： 标准的查找函数是匹配所有的元素值，另一个专用版本的查找函数是基于struct的一个单独属性值来匹配一个struct。 
-Find(Value): Value 是要搜索的值。 返回在数组中第一个匹配指定值的元素的索引，如果没有找到返回-1。 Value 可以是任何有效的表达式。
-Find(PropertyName, Value): PropertyName 是在struct中用于搜索的属性名称(必须是'Name'类型)， Value 是要搜索的值。 返回在数组中第一个匹配指定的属性名 PropertyName 的值的struct的索引，如果没有找到，返回-1。 Value 可以是任何有效的表达式。 
◆Sort(SortDelegate): 使用 SortDelegate 来适当地对数组的内容排序。 SortDelegate 的签名应该和以下显示的一样：
-delegate int ExampleSort(ArrayType A, ArrayType B) { return A < B ? -1 : 0; } // 一个负数返回值预示着应该交换这些项。