rational rose中对函数的形参设置

来源:互联网 发布:应用双开软件下载 编辑:程序博客网 时间:2024/05/22 15:07

一、其实rose功能非常强大和实用,给方法添加行参和实现重载都是可以的:


右击arguments窗口,弹出菜单的Insert项。就可以了!


二、顺序图的注意点

区分实用actor还是用对应的系统类:


看你顺序图的层级。如果是外部actor与系统交互顺序图,则用actor,因为主要是系统内外交互的描述。如果描述系统内部类之间的交互,则用类,因为涉及到方法的调用。

三、详细的介绍

1. Rose的作用
(1)项目开始阶段
产生使用案例模型
(2)细化阶段
开发程序的类框图,合作图,先是要开发的对象,及其相互间的交互。类框图显示对象间的相互关系。
(3)构造初始阶段
生成组件框图,显示系统组件间的相关性,并产生系统的框架代码。
(4)构造阶段
将新开发代码通过逆向工程转出到模型中,从而将开发阶段出现的变化反映到模型中。
(5)交接阶段
这个阶段,Rose主要用于在软件产品完成时更新模型。

2.如何选择缺省编程语言
例如选择VC++语言的方法是,Tools->Options->Notation->Default->VC++。

3. Use Case View的作用
Use Case视图包括系统中所有的角色、使用案例和Use Case框图(Use CaseDiagram),还可能包括一些Sequence和Collaboration框图。
项目开始时,UseCase视图的主要使用者是客户、分析人员和项目管理员。这些人利用使用案例、UseCase框图和使用文档来确定系统的高层视图。
使用案例只关注系统的作用,而不关注其实现细节。
4.Logic视图采用两步法
Logic视图采用两步法,首先标示分析类,然后标示设计类。所谓分析类就是和语言无关的。例如有Boundary类,Control类,Entity类等。而设计类就具有特定的语言特点,比如Java类,或者C++类。分析类和设计类没有一一对应关系。
5. Logic视图有什么作用
Logic视图关注的是系统的逻辑结构。在这个视图中,要标示系统组件,检查系统的信息和功能,检查组建之间的关系。这里重复使用是一个主要目的。通过认真指定类的信息和行为,组合类,以及检查类和包之间的关系,就可以确定重复使用类和包。完成多个项目后,你就可以将新类和包加进重复使用库中。今后的项目可以组装现有的类和包,而不必一切从头开始。

6.使用控制单元支持多用户并行开发
Rose通过控制单元支持多用户并行开发。Rose中的控制单元可以使UseCas视图、Logical视图或Compinent视图中的任何包。此外,Deployment视图和ModelProperties单元也可以进行控制。控制一个单元时,它存放在独立于模型其它部门的文件中。这样,独立文件可以利用支持SCC的版本控制攻击进行控制,如RationalClearCase、MicrosoftSourceSafe和Rose自带的基本工具。控制单元可以从浏览的模型中装入或卸载。使用控制工具还可以检查进口和出口(CheckedIn和Out)。

 

7.输入输出模型
面向对象机制的一大好处是重复使用,重复使用不仅适用于代码,也适用于模型。要充分利用重复使用功能。Rose支持输出与输入模型和模型元属。可以输出模型或部分模型。将其输入另一模型。
注意:要输出包或者类时,必须选定逻辑视图里的东西;而要输出模型,则是选定除此以外的东西。
8.Use case和role
使用案例和角色描述所建系统的范围,使用案例包括系统中的一切,角色包括系统外的一切。不考虑编程细节。使用案例是系统提供的高级功能块,角色是与所建系统交互的对象。

9.Use Case view如何安排更合理
use caseview中的main视图主要用来显示使用案例包。至于包里的使用案例可以放在另外建立的一个视图里,这个视图以包的名字来命名,这样可以和主视图(main)分开,使整个UseCase view更清晰。

10.关于Use Case view的几点规定
(1).不要建模角色之间的通信,因为角色在系统之外,管不了那么多;
(2).框图显示可用的使用案例但不管它们的执行顺序,所以不要在使用案例之间画箭头,除非是表示使用关系和扩展关系;
(3).每个案例都要由角色启动,也就是说它们之间要有一个箭头,使用关系和扩展关系除外;
(4).可以把数据库看成是整个UseCase框图下面的层,可以用一个使用案例在数据库中输入信息,然后在另一个使用案例中访问数据库中间的信息,不要在使用案例之间画箭头显示信息流程(与2同:使用案例之间不要随便画箭头,除非是表示使用关系和扩展关系)。

11.使用案例和传统方法不同
将项目分解成使用案例是个面向对象的过程而不是面向实现的过程,因此不同于传统的功能分解法。功能分解法关注如何分解成系统能处理的小块,而使用案例首先关注用户对系统的需求。

12.如何寻找使用案例
检查客户提供的文档,同时询问最终客户需要什么功能:
(1) 这个系统用来干什么?
(2) 用户是否要维护任何信息(生成、读取、更新、删除)?
(3) 用户是否要把外部事件告诉系统?
(4) 系统是否要把某些改变和事件告诉用户?

13.关于使用案例的几点建议
(1)使用案例独立于编程细节,它关注的是系统的功能而不是如何实现这个功能。
(2)使用案例是高级视图,不能太多,一般用户的使用案例的个数是20到50个。可以运用使用关系和扩展关系将使用案例进行必要的分解,也可以将使用案例组合成组,以便于组织。
(3)使用案例关注使用系统的用户。每个使用案例应表示用户与系统间的完整事务,为用户提供一定价值。使用案例应该按照业务属于命名,而不是按照计算机技术术语命名,应该让客户一目了然。使用案例通常用动词或动词短语命名,描述客户看见的最终结果,客户不关心实现这些需要采取什么具体步骤。
14.如何检查使用案例是否完整
(1)每个功能要求是否至少在一个使用案例中?如果要求不在使用案例中,则不会实现。
(2) 是否考虑每个用户如何使用系统?
(3)每个用户向系统提供了什么信息?
(4)每个用户从系统接收了什么信息?
(5)是否考虑了维护问题?要有人启动和关闭系统。
(6)是否标示了系统要交互的所有外部系统?
(7)每个外部系统从系统接收什么信息,向系统发送什么信息?

15.使用案例的细化——建挡事件流
(1)简要说明:描述该使用案例的作用;
(2)前提条件:开始使用案例时必须满足的条件;
(3)主事件流和其它事件流:使用案例的具体细节在主事件流和其它事件流中描述。事件流是关注系统干什么,而不是怎么干
a.使用案例如何开始;
b.使用案例的各种路径;
c.使用案例的正常(主)流程;
d.使用案例的主事件流的变形(其它事件流);
e.错误事件流;
f.使用案例如何结束。
(4)事后条件:使用案例结束后必须为真的条件。

16.使用案例的命名
模型中的每个使用案例应有唯一名称。使用案例应从客户角度命名,以帮助确定项目范围。使用案例名还应独立于实现方法。要避免使用使用案例与特定实现方法相联系的短语,如Internet.使用案例通常用动词和短语命名。

17.角色的分类
角色有三大类:系统用户、与所建系统交互的其他系统、时间。
时间作为角色时,经过一定时间触发系统的某个事件。例如,ATM机可能每天午夜运行一些协调处理。由于事件不在我们的控制之内,因此是个角色。

18.角色的版型
尽管有多种选择,但只能选择一种Actor。

19.角色基数
制定某个角色需要多少实例。

20.使用案例和角色支持四种关系
通信关系(communicates relationship),使用关系(usesrelationship),扩展关系(extends relationship),角色一般化(actorgeneralization)。
通信:角色和使用案例之间的关系;
使用:使一个使用案例可以使用另外一个使用案例提供的功能,使用关系通常用于构造一些两个或多个使用案例共同的可复用功能。如下图所示,验证过程(Authenticate)可以被共用。
扩展:使一个案例可以扩展另外一个使用案例的功能。它和使用关系类似,都是把共同功能分离到另一个使用案例中去,但在图例中箭头的方向刚好相反。
角色一般化:表示几个角色有一些共性。例如公司客户和个人客户都是客户,它们的关系如下图所示,左右两个图的分解层次不同
这种关系并非总是必需的。一般来说,只有在系统认为一种角色与另一种角色的表现不同时才需要。如果公司客户启动一些个人客户不启动的使用案例,则最好进行角色一般化。如果两种客户使用相同的使用案例,则没有必要进行角色一般化。如果两种客户使用相同的使用案例只是稍有不同,则仍然没必要进行角色一般化。细微差别可以在使用案例的事件流文档中表示。
21.关于使用案例、角色的小结
本章结束了如何使用使用案例、角色和UseCase框图。所建系统的要求组成所有使用案例和角色设置。首先生成主UseCase框图,显示系统的总体视图。然后可以生成其他框图。演示使用案例与角色的交互。使用案例可以使用和扩展其他使用案例。此外使用案例之间不能直接通信。一个使用案例总是需要另一是用案例的功能时,使用使用案例。一个使用案例可选利用另一是用案例的功能时,扩展使用案例。如果一个使用案例使用或扩展另一是用案例,则被利用者是现象使用案例。直接由角色参与的使用案例是具体使用案例。
角色可以和使用案例通信,演示哪个角色参与哪个使用案例。角色还可以相互继承。例如,学生可能是系统中的角色,我们要进一步将学生分为全日制和半日制学生。这时全日制和半日制学生都继承学生角色。

22.对象的持续性分类
(1)持续Persistent:保存到数据库或者其他的持续存储器中,如硬盘、光盘或软盘中。
(2)静态Static:静态对象保存在内存中,直到程序终止,不会保存在外部持续存储器中,相当于C++中的全局对象。
(3)临时Transient:临时对象只是短时间内保存在内存中。
注:如果将对象的类的持续性设置为Persistent,则对象的持续性可以设置为Persistent,Static或者Transient。如果将对象的类的持续性设置为Transient,则对象的持续性只能设置为Static或者Transient。
23.序列图和协作图的不同点
(1)只有序列图有控制焦点Focus of Control
(2)只有协作图有数据流:数据流是一个对象向另外一个对象发送消息后返回的值。
(3)协作图显示信息流,但不按时间显示。协作图显示对象间的关系和对象间的消息。从其中设计人员可以看到哪个对象是瓶颈,或发现那些对象需要直接相互通信。

24.消息的同步选择
(1)简单Simple:消息在单个控制线程中运行。
(2)同步Synchronous:客户发出消息后等待供应者响应这个消息。
(3)阻止Balking:客户发出消息给供应者,如果供应者无法立即接收消息,则客户放弃这个消息。
(4)超时Timeout:客户发出消息给供应者,如果供应者在指定时间无法接收消息。
(5)异步Asynchronous:客户发出消息后不管消息是否被接收,继续别的事物。
25.消息的频率
消息的频率可以让消息按规定时间间隔发送,例如每30秒发送一次。
(1)定期(Periodic):定期消息;
(2)不定期(Aperiodic):不定期消息,只发送一次,或者在不规则时间发送。

26.两步法生成交互图
第一步:关注客户关心的高级信息。这时候,对象还没有映射类,消息还没有映射操作。这些图只是让分析人员、客户和其他对业务流程感兴趣的人了解系统的逻辑流程。
第二步:客户统一第一部框图的流程后,小组加进更多细节。这时的框图对开发人员、测试人员以及项目的其他成员更有用,而对客户的作用不大。
首先,加入对象。可能加入控制对象,数据库连接对象,安全处理对象,错误处理对象等。
通常每个交互图有一个控制对象,负责控制情景中的程序。一个使用案例的所有交互图可能共享一个控制对象,因此,一个控制对象可以处理该使用案例的所有程序信息。
注意,控制对象并不进行任何业务处理,只是向其他对象发消息。控制对象负责协调其他对象的效果和委托责任。因此,控制对象有时也称为管理者对象。
使用控制对象的好处是能够将业务逻辑和程序逻辑分开。
其次,将每个对象映射到类。可以映射到现成的类或者新生成的类。
其次,将框图中每个消息映射操作。
其次,设计对象和消息的细节,设置对象的持续性、消息同步性和消息频率等。
最后,产生模型质量报告,显示未映射的对象和消息。
27.如何寻找类
(1)可以从使用案例的事件流开始,看看事件流中的名词即可知道某些类。
(2)检查交互图中的对象,通过对象的共性寻找类。
寻找类时要考虑三种不同的版型:Entity,Boundary,Control。

28.类的种类
普通类,参数化类,实例化类,类实用程序,参数化类实用程序,实例化类实用程序,元类。
(1)参数化类ParameterizedClass:用于生成一系列其他类,通常参数化类是某种容器,也称模板。在Detail->FormalArguments中设置参数的值。
(2)实例化类InstantiatedClass:具有实际变元值的参数化类。
(3)类实用程序ClassUtility:是一组操作,例如数学函数。类实用程序常用于扩展编程语言提供的功能或放置一组一般性可复用功能块让许多系统使用。
(4)参数化类实用程序ParameterizedClassUtilit
y:是生成类实用程序模板。
(5)实例化类实用程序InstantiatedClassUtility
:是设置了参数的参数化类实用程序。
(6)元类MetaClass:元类的实例是类而不是对象。参数化类和参数化类实用程序就是元类。

29.类的版型
三种:实体类Entity,边界类Boundary,控制类Control。
(1)边界类Boundaryclasses:位于系统和外界的交界处,包括所有窗体、报表、与打印机和扫描仪等硬件的接口。寻找边界类可以查找使用案例,每个“角色—使用案例”之间至少有一个边界类,有可能和别的“角色—使用案例”共用。
(2)实体类Entityclasses:保存要放进持续存储体的信息。实体类通常在事件流和交互图中,是对用户最有意义的类,通常用业务域术语命名。通常,数据库中可以对每个实体类生成一个表格。
(3)控制类Controclasses:协调其他类的工作。每个使用案例通常有一个控制类,控制使用案例中的时间的顺序。
注意:控制类本身不完成任何功能,其他类并不向控制类发送许多信息,而是有控制类发出许多信息,使用案例只是向其他类委托责任。为此,控制类也称管理类。
可能还有许多控制类是在许多使用案例之间共用的。这些控制类可以分析系统使用的功能。

30.设置类的可见性
Visibility选项确定包外能否访问这个类,有三个选项:
(1)Public:系统中其他所有类都可以访问这个类。
(2)Protected,Private:这个类可以在嵌套类、友类或同一各类中访问。
(3)Package orImplementation:这个类只能由同一包中的其他类访问。

31.类基数
可以设置类的实例数。可以设置基数的还有“角色”。

32.类的存储要求
注明每个类的相对或绝对内存需求量。
类实用程序,参数化类实用程序,实例化类实用程序不能用这个字段。
33.类的持续性
Persistent:类对象中的信息存储到数据库或者其他别的永久存储体。
类实用程序,参数化类实用程序,实例化类实用程序不能用这个字段。

34.设置类并发性
并发性描述类在存在多个控制线程时的表现。
Sequential:只有一个控制线程时,类正常工作,而在有多个控制线程时不能保证。
Guarded:存在多个控制线程时,类正常工作但不同线程中的类应该相互协作,保证不会互相干扰。
Active:类有自己的控制线程
Synchronous:存在多个控制线程时,类正常工作不需要与其他类相互协作,因为其他类本身能处理互斥情形。

34.在类框图中使用包
(1)按版型分包
如实体类包Entity,边界类包Boundary,控制类包Control。
(2)按功能分包
如安全包Security,错误处理包Error Handling……

35.如何查找属性
(1)查阅使用案例。寻找事件流中的名词。
(2)需求文档。需求中可能会介绍系统要求收集哪些信息,这些信息就是类的属性。
(3)检查数据库结构。如果已经定义数据库结构,则表中的字段就是属性。注意数据库表格和实体类并不总是一一对应。
类的属性不宜太多,如果太多可以分解成更小的类。类的属性个数最好控制在10到15个以下。同样属性个数也不要太少,太少的可以合并类。

36.如何区分属性和类
(1)考虑这个信息有没有行为,如果有则应作类处理;
(2)根据具体需要。

 


36.设置类的属性的包容
属性包容描述属性如何存放在类中。
按数值Byvalue:属性放在类中。例如,如果属性定义为字符串,则字符串放在类的定义中
按引用By reference:属性放在类外,类指向这个属性。
未指定Unspecified:没有指定包容类型。缺省设置。


37.设置类的属性为静态
这样属性成为所有这个类的对象共享的。


38.指定派生属性
是由其他属性生成的属性。


39.操作的类型
(1)实现者操作Implementoroperations:实现一些业务功能。实现者操作可从交互框图中找到。
每个实现者操作应该能回溯要求:需求—>使用案例—>事件流—>消息—>操作。
(2)管理者操作Manageroperations:管理对象的生成和构造。例如,类的构造器和删除器。
(3)访问操作AccessOperations:属性通常是专用或保护的,但其他类可能要浏览或改变某个类的属性,可以通过访问操作实现。
行业标准是对每个属性建立Get和Set操作。
(4)帮助器操作Helperoperations:是类完成任务所需的操作,其他类不需要知道这个操作。这时类的专用和保护操作。
通常,帮助器操作可以从交互框图找到,它们显示为反身消息。


40.标识操作的步骤
(1)检查交互框图。大多数消息是实现者操作,而反身消息可能是帮助器操作。
(2)考虑管理者操作。可能要增加构造器和删除器,但这不是必需的,Rose可自动产生。
(3)考虑访问操作。对需要被其他类浏览或改编的属性生成Get和Set操作,但这也可以为Rose自动产生。

41.操作的参数
也就是函数的参数。

 

43.指定操作协议
描述客户可以对对象进行的操作,以及操作执行的顺序。不影响代码生成。

 

44.指定操作限定
指定操作的语言特定限定。不影响代码生成。


45.指定操作异常
可以列出操作可能抛出的异常,不影响代码生成。

46.指定操作的长度
指定操作运行时所需的内存量,不影响代码生成。

47.指定操作时间
执行这个操作所需的大概时间量,不影响代码生成。

48.指定操作词法
可以制定操作的工作,可用伪代码或者用说明描述操作逻辑。不影响代码生成。


49.类与类之间的关系
类之间可以建立四种关系:关联、依赖性、累积和一般化。
(1)关联Associations:是类之间的词法连接,使一个类知道另一个类的公开属性和操作。关联有单向和双向之分。如果两个类是双向关联的,Rose将属性放进彼此类中。单向关联如下图所示,则Person知道House的公开属性和操作,而House不知道Person的。交互图中Person可以向House发消息,而House不可以向Person发消息。

通过交互图可以确定关联方向,如果交互图中总是Person向House发消息,则是从Person到House的单向关系。如果又有从House到Person的关系,则需要双向关系。
单向关联有助于标识可复用的类。如果House和Person间关系是双向的,则每个类都需要知道对方,因此两者都不能复用。任何输出多个单向关系的类都很难复用,而只接收单向关系的类则容易复用。如下图所示
(2)依赖性Dependencies:显示一个类引用另一个类,在C++中加入#include语句,因此被引用类的头文件的改变可能影响引用类。依赖与关联不同,首先依赖性总是单向的,显示一个依赖于另一个类的定义,其次Rose不对依赖性产生属性。如下所示,Client类依赖于Supplier类的定义。

(3)累积Aggregations:是强关联。累积关系是整体与个体间的关系。累积可以反身。累积关系生成代码。


(4)一般化Generalizations:显示类之间的继承关系。在UML中,继承关系被称为一般化,显示为子类指向父类的箭头。注意:继承的层数不可太多。
50.如何寻找类之间的关系
(1)首先检查交互图,如果类A向类B发出消息,则它们必须有关系。通常用这个方法找出的关系是关联和依赖性。
(2)检查类的整体/部分关系,任何由其他类组成的类都参与累积。
(3)检查类的一般化关系(即继承关系),寻找具有不同类型的类。
(4)检查类中的其他一般化关系。找出具有的大量共同点另外组装成一个新类。
一个类的关系不要太多,否则很难复用。设计良好的类的关系不多。

51.包的依赖性
如果包A中的某些类和包B中的某些类有单向关系,则这两包之间有依赖关系。如下图所示,包A依赖B。包B比A容易复用。

要尽量避免两个包之间的相互依赖,因为那样两者都不易复用。

52.类之间关系的若干细节
(1)倍增性:表示某一时刻一个类的几个实例和另外一个类的一个实例相联系。

(2)关系命名:关系可以用关系名和角色名调整,可以设置关系名的方向。
(3)版型
(4)作用:作用名可以在关联或累积关系中代替关系名,描述关系的作用。

(5)输出控制:在关联关系中,Rose在生成代码时生成属性。生成的属性的可见性通过ExportControl字段设置,和其他属性一样,有四个可见性选项:Public,Private,Protected,Package或Implementation。在双向关系中,可以设置两个属性的输出控制,各在关系的一端生成。在单向关系中,只需设置一个输出控制。输出控制可以用关系的specification窗口中的RoleA General和Role B General标签设置。
(6)使用静态关系:我们知道关联和累积会产生代码,Static字段确定生成的属性是否静态的,静态属性是类的所有实例共享的属性。如果将一个作用设置为静态的,则产生的关联属性为静态的。
(7)使用朋友关系:
朋友关系表示Client类可以访问Supplier类的非公开属性和操作。可以对关联、累积、依赖和一般化关系设置朋友属性。Supplier类的源代码包括让Client类具有朋友可见性的逻辑。
(8)设置包容:确定累积关系生成的属性按值或按引用包容。在累积关系中,整体类要加进表示每个部件类的属性。这里设置这些属性按值或按引用。
按值包容属性则同时生成和部署整体及其部件。
按引用包容属性则不同时生成和部署整体及其部件。
(9)使用限制符:用于缩小关联的范围。
例如,我们有个Person和Company类之间的关联。假设对某个PersonID值,有两个相关的公司,则可以在Person类中加上限制符PersonID。如下左图所示。

(10)使用链接元素:

(11)使用限制:限制是必须符合的条件。在Rose中,可以设置关系或单个作用的限制条件。输入的限制在生成代码时成为说明语句。
53.类的行为
如果一个类有一些重要的动态行为,就有必要建立状态图。
一个状态可以加进五个信息:活动,进入,退出,事件和状态历史。
(1)活动:对象在特定状态时进行的行为。活动在状态内显示,表示为:do
(2)进入:对象进入某个状态时发生的行为。进入在状态内显示,表示为:entry
(3)退出:对象退出某个状态时发生的行为。退出在状态内显示,表示为:exit
(4)事件:事件导致对象从一种状态变到另一个状态。事件在过渡箭头上显示。

 

54.什么是组件
组件是代码的物理模块,可以是代码库也可以是运行文件,如C++中的*.H,*.CPP和*.EXE都是单独的组件。
生成代码之前,将每个文件映射相应的组件。在C++中,每个类映射两个组件,一个是*.H,另一个是.CPP。
一旦生成组件后,它们加进Component框图中,并在其间画出关系。组件间的唯一关系是依赖,表示一个类要在另一个类之前编译。

55.源代码库组件的类型
(1)组件component:表示具有定义接口的软件模块;
(2)子程序规范和体subprogram specification 和body;
(3)主程序main program:主程序是包含程序根的文件;
(4)包规范和体package specification和body:包是类的实现方法。

56.运行组件的类型
(1)执行文件
(2)DLL
(3)任务规范和体task specification和body:表示具有独立控制线程的包,通常执行文件表示为具有.EXE扩展的任务规范。

55.代码生成的步骤
(1)检查模型
模型检查独立于语言。
Tools->checkmodel。常见的问题有:消息不映射操作,对象不映射类。
report->show accessviolations,它可找出不同包中两个类存在关系时发生的问题。
(2)生成组件
这个步骤C++不是必需的;
(3)将类映射组件
将Logic框图中的类拖到Component框图中对应的组件;
标识组件之间的依赖性。
(4)设置代码生成属性
类、属性、组件和其他模型元素可以设置多个代码生成属性。
Rose提供常用缺省设置Tools->Optoins。
缺省设置的改变影响所有使用该设置的模型。如果只想修改单个模型的生成属性,请打开该模型的规范窗口,选择语言标签并在此改变属性。
克隆属性设置:与其直接改变缺省设置值,不如先克隆属性设置,再对备份进行更改。强烈建议保持原有的缺省设置,只改变克隆属性设置。
(5) 选择类、组件和包
生成代码时,可以一次生成一个类、一个组件或一个包。
(6)生成代码
Rose只能生成程序框架。生成框架后,开发人员利用它编码类的每个操作,设计图形用户界面。
56.如何设置VC++的代码生成属性
(1)如何缺省生成Get()和Set()
Tools->Visual C++->Property:The Accessors tab controlswhether or not accessor methods are generated for a modeled role orattribute. Default is not to generate Get and Set accessors. Ifchecked, Get or Set accessors are generated when the class isgenerated for the first time, but only if the Apply Pattern on CodeGeneration switch (on the Visual C++ Properties' Code Update tab)is also checked.
(2)Tools->Options->Visual C++

0 0
原创粉丝点击