标签: anti-patterns

使用D字符串mixins进行代码重用是一种反模式吗?

对于那些不熟悉D字符串mixins的人来说,它们基本上是编译时间的.您可以获取任何编译时字符串(无论是文字还是通过模板元编程或编译时函数评估生成)并将其编译为代码.如果你使用一个简单的字符串文字,它基本上是编译器自动复制粘贴.

您是否认为使用字符串混合文字作为简单代码重用的方法是反模式,而其他分解方法不太合适?一方面,它基本上是编译器自动化的文字复制和粘贴,这意味着一旦混合在实例中就没有任何关系.如果字符串mixin中的符号与混合范围中的符号发生碰撞,则会发生错误(尽管在编译时,而不是在运行时).它是相对非结构化的,例如,可以将一个字符串混合到一个函数的中间,当且仅当范围中的变量根据某个约定命名时才会起作用.Mixins还可以声明外部作用域随后可以使用的变量.

另一方面,因为复制和粘贴是编译器自动化的,所以在源代码级别的代码有一个单一的真实点,如果需要修改它,它只需要在一个地方修改,一切都保持同步.字符串mixins还大大简化了重用代码,这些代码很难以任何其他方式考虑因素,否则很有可能被手动剪切和粘贴.

d anti-patterns cut-and-paste

7
推荐指数
1
解决办法
1300
查看次数

为什么在原型中定义属性被认为是反模式

我经常看到这种模式来定义javascript对象

function Person(name) {
    this.name = name;
}
Person.prototype.describe = function () {
    return "Person called "+this.name;
};
Run Code Online (Sandbox Code Playgroud)

本文中,它表示直接向原型对象添加属性被视为反模式.

来自"基于经典类"的语言,除了方法之外必须定义属性听起来不太正确,不过在javascript中,方法应该只是具有函数值的属性(我在这里吗?)

我想知道是否有人可以解释这个,甚至建议一个更好的方法来处理这些情况

javascript prototype anti-patterns prototypal-inheritance prototype-programming

7
推荐指数
2
解决办法
1662
查看次数

是将多个@Service和@Repository类分组为包装反模式?

问题有点夸夸其谈.我和同事就以下模式发生了争执:

@Component
public class MetaService {

    public static UserService userService;
    public static GroupService groupService;   
    public static PermissionService permissionService;            
    // ...more fields

    @Autowired
    public MetaService(UserService userService,
                       GroupService groupService
                       PermissionService permissionService) {

        MetaService.userService = userService;
        MetaService.groupService = groupService;
        MetaService.permissionService = permissionService;           
    }
}
Run Code Online (Sandbox Code Playgroud)

基本上,MetaService是多个Spring bean @Service类的入口点/包装器.而且还有一个类似于bean类的MetaDao包装器@Repository:

@Component
public class MetaDao {

    public static UserDao userDao;
    public static GroupDao groupDao;
    public static PermissionDao permissionDao;
    // ...more fields   

    @Autowired
    public MetaDao(UserDao userDao,
                   GroupDao groupDao,
                   PermissionDao permissionDao) { …
Run Code Online (Sandbox Code Playgroud)

java spring design-patterns dependency-injection anti-patterns

7
推荐指数
1
解决办法
141
查看次数

是否有正当理由将数据内部保存为XML?

在我进入工作岗位的那些年里,我注意到了一种我认为是反模式的明显趋势:将内部数据维护为XML的大字符串.我已经看到这种做法有很多不同的方式,尽管两个最严重的罪犯非常相似.

Web服务

第一个应用程序是Web服务,可以访问SQL数据库中可能存在的大量数据.在启动时,它会将数据中的所有数据或多或少地从数据库中提取出来,并将其作为XML存储在内存中.(三次.)此应用程序的所有者将其称为缓存.我称之为缓慢,因为在对抗此问题时遇到的每个性能问题都可以直接追溯到这个问题.(这是一个企业环境,客户端因为性能故障而不是服务而受到指责应该不足为奇.)此应用程序确实使用了XML DOM.

进口商

第二个应用程序读取作为从第三方数据库导出的结果生成的XML文件.目标是将此数据导入专有系统(由我们拥有).执行此操作的应用程序读取整个XML文件,并在整个导入序列中维护至少两个(有时多达四个)XML文件的副本.请注意,可以在导入之前对数据进行操作,转换和配置,因此导入器在整个生命周期内都以XML格式拥有此数据.不出所料,当提供中等大小的XML文件时,此导入程序会爆炸.此应用程序仅将XML DOM用于其中一个副本,其余都是原始XML字符串.

我对常识的理解表明,XML 不是用于在内存中保存数据的良好格式,而是在读取和导入时,数据在输出/传输和转换为内部数据结构时应转换为XML.问题是,我经常遇到完全忽略可扩展性问题的生产代码,并且经历了大量额外的努力.(在这些应用程序中,字符串解析的绝对数量令人恐惧.)

对于其他人遇到的工作来说,这是一个常见的失败吗?或者这只是我的运气不好?或者我错过了一些令人眼花缭乱的明显和良好的情况,哪些是正确的,可以将大量数据存储在内存中作为XML?

xml language-agnostic anti-patterns

6
推荐指数
1
解决办法
255
查看次数

企业架构反模式

在为企业构建应用程序时要避免哪些关键的反模式?我们正在使用C#和SQL Server以及Silverlight,但是我认为一些反模式将是语言中立的.

architecture design-patterns anti-patterns

6
推荐指数
1
解决办法
2003
查看次数

依赖注入 - 与数据传输对象(DTO)一起使用?

考虑下面的代码(已经简化).我有一个服务类,它返回一个特定DTO对象的列表,每个对象都实现自己的特定接口.在实际代码中,当我使用遗留代码时,通过迭代数据集来填充这些代码.

问题:

  1. 我们如何创建/使用DTO而不用新增或使用Service Locator反模式?在Composition Root中组合一个空的DTO对象并通过构造函数将它注入Service类没有多大意义,因为我实际上在填充列表时使用DTO作为排序的临时变量.

  2. 在代码中,您可以看到我新建DTO的示例.但是,如果我首先让DTO不实现接口,这并没有好多少.那么,他们不应该实现接口,因此不使用DI与DTO?


public class Services : IServices
{    
    public IList<IDTO> GetDTOs()
    {    
        ...
        List<IDTO> dtos = new List<IDTO>();
        foreach (c in d) 
        {
            DTO dto = new DTO();
            dto.x = c.x;
            dto.y = c.y;
            dto.z = c.z;
            dtos.Add(dto);
        }
        return dtos;
    }    
}
Run Code Online (Sandbox Code Playgroud)

dependency-injection anti-patterns interface dto service-locator

6
推荐指数
2
解决办法
3136
查看次数

DI Control-Freak反模式:理解困难

我正在阅读Mark Seemann的.NET中的依赖注入,我不能为我的生活让我的头脑缠绕:

虽然关键字在涉及挥发性相关性时是一种代码味道,但您不必担心将其用于稳定依赖性.在新的关键字不是一般突然"非法",但你应该使用它来获得挥发性依赖实例避免.

也许是因为我仍然不能把我的脑袋缠绕在环境上下文中,而不仅仅是一个全局变量,但我只是没有得到作者所说的内容.

我真的很想从上到下理解DI,但是现在我被卡住了,这只是书中的1/3 ... Control-Freak反模式似乎是每一个曾经生活过的程序员...

有人有任何见解吗?

.net design-patterns dependency-injection anti-patterns

6
推荐指数
1
解决办法
1116
查看次数

GWT ClientFactory:这不仅仅是一个巨大的blob/monolith吗?

GWT ClientFactory似乎是GWT应用崭露头角的新的设计模式,虽然不是正式的GWT API的一部分,是由GWT鼓励和无数的GWT/MVP的例子中找到.

想要这个ClientFactory概念.但是我担心的是:对于拥有许多屏幕,显示区域和复杂架构的非常大的应用程序,单个应用ClientFactory程序将成为数据结构的巨大整体,可能有数百种getter方法.

那么请问:这是?为什么这样的整体设计鼓励和接受GWT,而不是其他(一般)应用.更重要的是,有没有办法将广泛分解ClientFactory为工厂对象的层次结构,以帮助代码可维护性,依赖性/引用等?

如果是这样,是否会将一个分解ClientFactory成较小的工厂,每个工厂负责注入应用程序的不同部分以及必要的视图,演示者等?

java gwt dependency-injection anti-patterns

6
推荐指数
1
解决办法
699
查看次数

像isInUnitTest()这样的检查是反模式吗?

我正在开发一个个人项目(意思是干净的源代码,没有遗留的依赖项),并尝试遵循有关单元测试,依赖关系管理等的最佳实践.

我公司的代码库充满了这样的代码:

public Response chargeCard(CreditCard card, Money amount) {
  if(Config.isInUnitTests()) {
      throw new IllegalStateException("Cannot make credit card API calls in unit tests!");
  }
  return CreditCardPOS.connect().charge(card, amount);
}
Run Code Online (Sandbox Code Playgroud)

这里的目标是主动防止在测试期间执行具有外部依赖性的危险代码/代码.如果单元测试做坏事我喜欢快速失败的概念,但我不喜欢这个实现有几个原因:

  • 它为Config整个代码库中分散的静态类留下了隐藏的依赖关系.
  • 它改变了测试和实时行为之间的控制流程,这意味着我们不一定要测试相同的代码.
  • 它为配置文件或其他一些状态保持实用程序添加了外部依赖项.
  • 看起来很难看:)

我可以通过更好的依赖感知来避免在我公司的代码库中使用它的相当多的地方,我试图这样做,但仍然有一些地方我仍然在努力去实现一种isInUnitTests()方法.

使用上面的信用卡示例,我可以isInUnitTests()通过在一个可模拟的CardCharger类或类似的东西中正确地将它包装起来来避免对每次充电的检查,但是虽然我觉得我只是将问题提升到一个级别 - 如何做我阻止单元测试构建一个真实的实例CardCharger而不检查创建它的构造函数/工厂方法?

  • isInUnitTests()一个代码味道?
  • 如果是这样,我怎么能继续强制单元测试不能达到外部依赖?
  • 如果没有,那么实施这种方法的最佳方法是什么,以及何时使用/避免它的好方法是什么?

为了澄清,我试图阻止单元测试访问不可接受的资源,如数据库或网络.我喜欢依赖注入的测试友好模式,但如果粗略的开发人员(即我)可能会违反好模式,那么好的模式就没用了 - 在单元测试做事情的情况下,对我来说快速失败似乎很重要不应该,但我不确定最好的方法.

language-agnostic unit-testing design-patterns anti-patterns

6
推荐指数
1
解决办法
278
查看次数

产生深度调用堆栈的代码是否被视为反模式?

我们正在围绕LLVM库进行研究,我们发现IR库有时会达到最多29个方法调用的调用堆栈.

有时当我在iOS框架中看到一些崩溃时,我也会观察到相当深的调用堆栈.

我的问题是,我们是否可以推断一个代码的设计是否存在问题,而这个代码的设计自称是如此之大.

这是一个例子:

/usr/local/LLVM/llvm/unittests/IR/AttributesTest.cpp:54
  /usr/local/LLVM/llvm/lib/IR/LLVMContext.cpp:162
    /usr/local/LLVM/llvm/lib/IR/LLVMContext.cpp:162
      /usr/local/LLVM/llvm/lib/IR/LLVMContextImpl.cpp:54
        /usr/local/LLVM/llvm/lib/IR/LLVMContextImpl.cpp:59
          /usr/local/LLVM/llvm/lib/IR/Module.cpp:60
            /usr/local/LLVM/llvm/lib/IR/Module.cpp:62
              /usr/local/LLVM/llvm/lib/IR/Module.cpp:456
                /usr/local/LLVM/llvm/lib/IR/Function.cpp:350
                  /usr/local/LLVM/llvm/lib/IR/BasicBlock.cpp:98
                    /usr/local/LLVM/llvm/include/llvm/ADT/ilist.h:282
                      /usr/local/LLVM/llvm/include/llvm/ADT/ilist.h:267
                        /usr/local/LLVM/llvm/lib/IR/SymbolTableListTraitsImpl.h:76
                          /usr/local/LLVM/llvm/lib/IR/BasicBlock.cpp:90
                            /usr/local/LLVM/llvm/lib/IR/SymbolTableListTraitsImpl.h:58
                              /usr/local/LLVM/llvm/lib/IR/ValueSymbolTable.cpp:75
                                /usr/local/LLVM/llvm/lib/IR/ValueSymbolTable.cpp:47
                                  /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:132
                                    /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:112
                                      /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:122
                                        /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:96
                                          /usr/local/LLVM/llvm/include/llvm/IR/Value.h:777
                                            /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:132
                                              /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:122
                                                /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:75
                                                  /usr/local/LLVM/llvm/include/llvm/IR/Value.h:771
                                                    /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:132
                                                      /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:122
                                                        /usr/local/LLVM/llvm/include/llvm/Support/Casting.h:75
                                                          /usr/local/LLVM/llvm/include/llvm/IR/Value.h:759
Run Code Online (Sandbox Code Playgroud)

PS示例调用堆栈实际上是由LLVMContext类的析构函数生成的:LLVMContext::~LLVMContext().这是来自Java世界的一篇非常古老的帖子的另一个例子:Java调用栈 - 从HTTP到JDBC作为图片.

callstack anti-patterns llvm

6
推荐指数
1
解决办法
563
查看次数