“你好世界” - TDD 方式?
自从我接触 TDD 以来,我一直在思考这个问题。 构建“Hello World”应用程序的最佳方法是什么? 这将在控制台上打印“Hello World” - 使用测试驱动开发。
我的测试会是什么样子? 以及大约什么班?
请求:没有指向什么是 TDD 的“类似于维基百科”的链接,我很熟悉 TDD。 只是好奇如何解决这个问题。
Well I have been thinking about this for a while, ever since I was introduced to TDD.
Which would be the best way to build a "Hello World" application ? which would print "Hello World" on the console - using Test Driven Development.
What would my Tests look like ? and Around what classes ?
Request: No "wikipedia-like" links to what TDD is, I'm familiar with TDD. Just curious about how this can be tackled.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(10)
您需要将控制台隐藏在界面后面。 (无论如何,这可以被认为是有用的)
编写测试
编写程序
重构为更有用的东西;-)
You need to hide the Console behind a interface. (This could be considered to be useful anyway)
Write a Test
Write the program
Refactor to something more useful ;-)
演示者视图? (模型似乎并不是严格必要的)
View 是将输出传递到控制台的类(简单的单行方法)
Presenter 是调用 view.ShowText("Hello World") 的接口,您可以通过提供来测试它存根视图。
不过,为了提高生产力,我只需要编写该死的程序:)
一个测试就足够了(用伪代码):
Presenter-View? (model doesn't seem strictly necessary)
View would be a class that passes the output to the console (simple single-line methods)
Presenter is the interface that calls view.ShowText("Hello World"), you can test this by providing a stub view.
For productivity though, I'd just write the damn program :)
A single test should suffice (in pseudocode):
嗯...我还没有见过 hello world 的 TDD 版本。 但是,要了解使用 TDD 和可管理性解决的类似简单问题,您可以查看 企业 FizzBuzz(代码)。 至少这会让您看到在 hello world 中可能实现的过度设计水平。
Well...I've not seen a TDD version of hello world. But, to see a similarly simple problem that's been approached with TDD and manageability in mind, you could take a look at Enterprise FizzBuzz (code). At least this will allow you to see the level of over-engineering you could possibly achieve in a hello world.
伪代码:
在生产代码中,您使用提示而不是模拟。
经验法则:
Pseudo-code:
In production code, you use the prompt instead of the mock.
Rule of thumb:
一个非常有趣的问题。 我不是 TDD 的大用户,但我会提出一些想法。
我假设您要测试的应用程序是这样的:
现在,由于我想不出任何直接测试它的好方法,所以我将把编写任务分解到一个接口中。
像这样分解应用程序
现在,您有了一个指向该方法的注入点,该方法允许您使用您选择的模拟框架来断言使用“Hello World”参数调用 WriteLine 方法。
我尚未解决的问题(我对输入感兴趣):
如何测试 ConsoleWriter 类,我想你仍然需要一些 UI 测试框架来实现这一点,如果你有这个,那么整个问题就在无论如何都没有实际意义...
测试主要内容方法。
为什么我觉得我通过将一行未经测试的代码更改为七行代码而取得了一些成就,其中只有一行代码经过了实际测试(尽管我猜覆盖率已经上升了)
A very interesting question. I'm not a huge TDD user, but I'll throw some thoughts out.
I'll assume that the application that you want to test is this:
Now, since I can't think of any good way of testing this directly I'd break out the writing task into an interface.
And break the application down like this
Now you have an injection point to the method that allows you to use the mocking framework of your choice to assert that the WriteLine method is called with the "Hello World" parameter.
Problems that I have left unsolved (and I'd be interested in input):
How to test the ConsoleWriter class, I guess you still need some UI testing framework to achieve this, and if you had that then the whole problem in moot anyway...
Testing the main method.
Why I feel like I've achieved something by changing one line of untested code into seven lines of code, only one of which is actually tested (though I guess coverage has gone up)
假设您了解单元测试,并且假设您了解 tdd“红绿重构过程”(因为您说过您熟悉 TDD),我将快速解释典型的 tdd 思维过程。
如果您考虑某个特定的问题单元,并且应该根据依赖关系来考虑所有其他相关事物,那么您的 TDD 生活将会变得更加轻松。 这是一个示例
场景:-
我希望我的程序在控制台上显示 hello world。
tdd 思考过程:-
“我认为我的程序将开始运行,然后调用控制台程序将我的消息传递给它,然后我希望我的控制台程序将其显示在屏幕上”
“所以我需要在运行程序时进行测试,它应该调用控制台程序“
”现在有哪些依赖项?嗯,我知道控制台程序是其中之一,我不需要担心控制台如何将消息发送到屏幕(调用io设备,打印和所有这些)我只需要知道我的程序成功调用了控制台程序,我需要相信控制台程序可以工作,如果没有,那么目前我不负责测试并确保它工作。我想测试的责任是我的程序在启动时调用控制台程序“
”,但我什至不知道要调用哪个控制台程序,但我知道 System.console.Writeline (具体实现)。那么,由于需求的变化,这可能会在未来发生变化,那么我该怎么办?”
“好吧,我将依赖于接口(或抽象)而不是具体实现,然后我可以创建一个假控制台来实现我可以测试的接口”
我已经放置了 IsCalled 成员,如果控制台程序发生,其“状态”将会改变被称为
“好吧”,我知道这听起来像是一个漫长的思考过程,但它确实得到了回报。 Tdd 迫使您在编码之前思考哪个比在思考之前编码更好
最终,您可能会想出类似以下方式来调用您的程序:
我将控制台传递给 my_program,以便 my_program 将使用控制台来编写我们的信息显示在屏幕上。
我的 my_program 可能如下所示:
最终的单元测试将是:-
Assuming you know unit testing, and asuming you understand the tdd "red green refactor process" (since you said you are familiar with TDD) Ill quickly explain a typical tdd thought process.
Your TDD life will be made a lot easier if you think of a particular unit of problem and every other connected things should be thought of in terms of dependencies. here is a sample
scenario:-
I want my program to display hello world on the console.
tdd thought process:-
"I think my program will start running then call the console program passing my message to it and then I expect my console program to display it on the screen"
"so i need to test that when i run my program, it should call the console program "
"now what are the dependencies? hmm I know that the console program is one of them. I don't need to worry about how the console will get the message to the screen (calling the io device, printing and all that) I just need to know that my program successfully called the console program. I need to trust that the console program works and if it doesn't, then at the moment i am not responsible for testing and making sure it works. the responsibility I want to test is that my program when it starts up calls the console program. "
"but i don't even know exactly what console program to call. well I know of System.console.Writeline (concrete implementation) but then this may change in future due to change in requirements, so what do i do?"
"Well , I will depend on interface (or abstraction) rather than concrete implementation, then i can create a fake console implementing the interface which i can test against"
I have put IsCalled member whose "state" will change if whe ever the console program is called
OK I know it sounds like a long thought process but it does pay off. Tdd forces you to think before codeing which is better then coding before thinking
At the end of the day, you may then come up with something like the following way to invoke your program:
I passed console to my_program so that my_program will use console to write our message to the screen.
and my my_program may look like this:
the final unit test will then be :-
在 java 中,您可以捕获(“重定向”)System.out 流并读取其内容。 我确信在 C# 中也可以完成同样的事情。 java中只有几行代码,所以我确信C#中不会多出多少行代码
In java you could capture ("redirect") the System.out stream and read its contents. I'm sure the same could be done in C#. It's only a few lines of code in java, so I'm sure it won't be much more in C#
我真的不得不反对这个问题! 所有方法论都有其用武之地,TDD 在很多地方都表现出色。 但用户界面是我真正放弃 TDD 的第一个地方。 在我看来,这是 MVC 设计模式的最佳理由之一:以编程方式测试模型和控制器的性能; 目视检查您的视图。 您所说的是对数据“Hello World”进行硬编码并测试它是否到达控制台。 要使用相同的源语言进行此测试,您几乎必须虚拟控制台对象,这是唯一可以执行任何操作的对象。
或者,您可以在 bash 中编写测试脚本:
添加到 JUnit 测试套件有点困难,但有些事情告诉我这从来都不是计划......
I really have to object to the question! All methodologies have their place, and TDD is good in a lot of places. But user interfaces is the first place I really back off from TDD. This, in my humble opinion is one of the best justifications of the MVC design pattern: test the heck out of your models and controller programmatically; visually inspect your view. What you're talking about is hard-coding the data "Hello World" and testing that it makes it to the console. To do this test in the same source language, you pretty much have to dummy the console object, which is the only object that does anything at all.
Alternately, you can script your test in bash:
A bit difficult to add to a JUnit test suite, but something tells me that was never the plan....
我同意大卫·伯杰的观点; 分离接口,并对模型进行测试。 在这种情况下,“模型”似乎是一个返回“Hello, world!”的简单类。 测试看起来像这样(在 Java 中):
我在 http://ziroby.wordpress.com/2010/04/18/tdd_hello_world/ 。
I agree with David Berger; separate off the interface, and test the model. It seems like the "model" in this case is a simple class that returns "Hello, world!". The test would look like this (in Java):
I've created a write up of solving
Hello World
TDD style at http://ziroby.wordpress.com/2010/04/18/tdd_hello_world/ .我猜是这样的:
I guess something like this: