我最近花了很多时间来执行我编写的各种SW组件的详细UML设计.回顾一下我最近完成的事情,并将其与我第一次学习UML时的情况进行比较,我发现我现在几乎严格使用聚合和组合关系,并且几乎放弃了"香草"非定向/定向关系.我当然仍然使用泛化和实现,但这些与上面的明显不同,并不被视为此问题的一部分.
在我看来,聚合/组合意味着"香草"联想的含义相同,等等.聚合和组合自然意味着一个方向,任何现代UML程序仍然允许您在聚合/组合关系上定义多重性并将动词应用于关系.那时,我认为香草协会的目的不大.
我理解有些人很难理解聚合和组合之间的区别.在早期,我有点难以理解他们的差异,我相信混淆是我使用香草协会的部分原因.我现在处于这样的地步,我看到很少或没有使用香草协会,并且实际上不喜欢看到它们被使用,因为我相信它们会留下一些问题(特别是两个对象之间强大或弱的生命周期关系).我相信香草协会唯一的实际用途是当你对手头问题的理解还没有发展到足以确定聚合和成分之间的生命周期差异时.在这种情况下,最好至少表明关系存在,然后当您更好地理解手头的问题时,您可以回来并适当地改变它.
长话短说,我相信人们使用香草协会的绝大多数时间,他们可以更准确地描述为聚合,有时作为一个组合.在我的信念中,我是非常错的吗?我错过了什么吗?让我听听吧!
有效的Java以及其他来源表明我们应该考虑使用组合而不是继承.通常使用Decorator模式并实现将调用委托给包装对象的转发方法,我经常发现自己实现了这样的组合.
但是,我经常发现自己编写了许多类型的简单转发方法:
public void myMethod(String name) {
instance.myMethod(name);
}
Run Code Online (Sandbox Code Playgroud)
无论如何在Eclipse(3.4.x)中自动生成这些转发方法?
我正在制作一个维护数字列表的简单程序,我希望这个列表也有一个名字.哪种方法最好:让我的列表类扩展ArrayList还是让它包含一个ArrayList成员?在这两种情况下,当然都会有一个"名称"字符串成员.
第一种方法意味着我只需要为名称实现getter和setter,但我认为这会使我的类与特定实现过于紧密联系?例如,如果我想稍后使用Vector,那么我必须在任何地方更改代码.
第二种方法可以更容易地改变实现,但当然现在变得非常烦人,因为我必须实现一堆包装器.
我已经阅读了关于继承与组合的SO帖子,因为我的列表是一种ArrayList,所以我倾向于第一种方法.但是,讨论是否存在任何差异,因为我正在扩展Collection类vs扩展通用类?还是我过度思考这个?
有没有办法超载,比如>>操作员的功能组合?操作员应该在lambda上无缝地工作std::function?
要求:
bind调用,这是一个快速而肮脏的示例,说明了所需的行为:
#include <iostream>
#include <functional>
using namespace std;
// An example of a quick and dirty function composition.
// Note that instead of 'std::function' this operator should accept
// any functional/callable type (just like 'bind').
template<typename R1, typename R2, typename... ArgTypes1>
function<R2(ArgTypes1...)> operator >> (
const function<R1(ArgTypes1...)>& f1,
const function<R2(R1)>& f2) {
return [=](ArgTypes1... args){ return f2(f1(args...)); };
}
int main(int argc, char **args) {
auto l1 = [](int …Run Code Online (Sandbox Code Playgroud) 到目前为止我取得的成就:
使用AVFoundation服务,我在UIView中放置了一个用户可以播放,暂停等视频(使用AVPlayer,AVPlayerItem,AVPlayerLayer等)
我在视图顶部放置了一个UIView(透明/清晰的背景颜色),用于显示播放的视频.我还处理了UIKit触摸事件,根据用户交互绘制线条.
现在,当我播放视频并触摸覆盖在该视图上的UIView时,我可以看到在播放视频上绘制的线条.
我想做的事:
用户完成绘图后(他认为它叠加在视频上),我希望我的应用程序编写原始视频和用户交互(绘制,删除等行),并将结果导出为另一个视频文件.
任何帮助或示例代码将受到高度赞赏.
我想知道共同墙(位于相邻房间)和房间之间的关系.
我知道房间和墙壁之间的关系是Composition not Aggregation(我是对的吗?)
And according to the definition of 组合 the contained object can't be shared between two containers, whereas in 聚合 it is possible.
现在我很困惑,最好的建模方法是什么,以表示共同墙和旁边的房间之间的关系?
如果您能为您的建议提供一些代码,那将是非常赞赏的.
| -------- | -------- |
Approch1:
(wall class ---- room class) /Composition
Run Code Online (Sandbox Code Playgroud)
Approach2:
wall class ----- room class /Aggregation
Run Code Online (Sandbox Code Playgroud)
Approch3:
我们有一个墙类和一个公共墙类,公共墙类继承自墙类
adjoining room class ---- (1) Common wall class /Aggregation
adjoining room class ---- (6) wall class / composition
Run Code Online (Sandbox Code Playgroud)
方法4: 我是开发人员而非设计师:)所以这是我的想法:
class Room
{
private wall _firstwall ;
private …Run Code Online (Sandbox Code Playgroud) 在这个例子中,我想我有大约4行代码可以用函数封装,而且这个函数肯定会用在同一层次结构中的其他类中.
我有以下选项来重用该代码:
我绝对不会做1或4.我过去会做2但是我试图继续保留组合而不是继承原则所以我倾向于4但是对于最有可能的东西似乎很多永远不要在层次结构之外使用,只有4行.我知道这是非常挑剔的,但我想弄清楚这样做的正确方法.
我们有使用贷款模式的测试装置.利用此模式创建运行测试所需的"种子数据".当测试依赖于数据时例如以下
"save definition" should {
"create a new record" in withSubject { implicit subject =>
withDataSource { implicit datasource =>
withFormType { implicit formtype =>
val definitn = DefinitionModel(-1, datasource.id, formtype.id, subject.role.id, Some(properties))
}
}
}
Run Code Online (Sandbox Code Playgroud)
其中withSubject,withDataSource,withFormType是测试夹具返回subject,dataSource,formType从数据库数据分别.withDataSource夹具需要subject隐含.建筑DefinitionModel要求datasource.id和formtype.id.所以根据测试的数据要求调用这样的数据构建器夹具会产生很多嵌套的夹具情况.有没有更好的方法来"组合"/构建这样的灯具?
我一直在阅读有关在JS中进行OOP的不同方法.
Douglas Crockford有一种有趣的方法,他似乎根本不使用授权.相反,对我而言,他似乎纯粹利用对象连接作为他的继承机制,但是我很难说出最新情况,我希望有人可以提供帮助.
以下是克罗克福德在其中一次会谈中提出的一个例子.
function constructor(spec) {
let {member} = spec,
{other} = other_constructor(spec),
method = function () {
// accesses member, other, method, spec
};
return Object.freeze({
method,
other
});
}
Run Code Online (Sandbox Code Playgroud)
以下是一个要点的例子
function dog(spec) {
var { name, breed } = spec,
{ say } = talker({ name }),
bark = function () {
if ( breed === 'chiuaua' ) {
say( 'Yiff!' );
} else if ( breed === 'labrador' ) {
say('Rwoooooffff!');
}
};
return …Run Code Online (Sandbox Code Playgroud) 作为RPG游戏后端的一部分,我希望能够对角色应用临时效果.这些效果的性质可能会有很大差异,但我想保持定义它们的方法非常简单.
我正在使用自定义事件处理作为mixin:
var EvtObject = {};
$rpg.Event.enable(EvtObject); // Add the 3 methods and set EvtObject._events = {}
Run Code Online (Sandbox Code Playgroud)
我想将Auras(临时效果)定义为具有事件处理代码的构造函数:
var MyAura = function(any, args){
this.group = "classification";
this.on( "tick", function(){} );
this.on( "remove", function(){} );
};
Run Code Online (Sandbox Code Playgroud)
然后应用为MyCharacter.addAura(new MyAura(any, args));.如您所见,我希望该this.on()函数在构造函数中可用.如果我使用mixin($rpg.Event.enable(MyAura.prototype))扩展MyAura原型,那么MyAura的每个实例都会引用_events原型中的相同对象.
我想知道以下解决方案是否是良好的做法:
Aura.create = function(Constructor)
{
Constructor.prototype = Aura.getPrototype(); // Aura specific prototype
return function()
{
var newAura = Object.create(Constructor.prototype);
$rpg.Event.enable( newAura );
Constructor.apply( newAura, arguments );
return newAura;
};
};
// Then creating new …Run Code Online (Sandbox Code Playgroud) composition ×10
inheritance ×3
aggregation ×2
c# ×2
java ×2
javascript ×2
oop ×2
associations ×1
avfoundation ×1
c++11 ×1
closures ×1
delegation ×1
eclipse ×1
ios ×1
lambda ×1
mixins ×1
object ×1
relationship ×1
scala ×1
scalatest ×1
sdk ×1
uml ×1
video ×1