Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > Unit testing in C

Reply
Thread Tools

Unit testing in C

 
 
Ian Collins
Guest
Posts: n/a
 
      10-04-2011
On 10/ 4/11 11:37 AM, nroberts wrote:
> On Oct 3, 3:30 pm, Jorgen Grahn<(E-Mail Removed)> wrote:
>> On Mon, 2011-10-03, nroberts wrote:
>>> On Oct 3, 1:27 pm, James Kuyper<(E-Mail Removed)> wrote:

>> ...
>>>> Testability shouldn't have much affect on your code design. If it does,
>>>> you're doing something wrong, either in your design or your testing.

>>
>>> I can't say I agree with that at all. One could argue of course that
>>> sure, in fact by definition it is correct since one major bonus of
>>> doing unit testing is that it forces good design, and one main reason
>>> why legacy code in notoriously untestable is because it lacked this
>>> force.

>>
>> I partly agree and partly disagree with that. Partly disagree, because
>> there are designs which make perfect sense for the program itself, but
>> are impossible for unit testing.
>>
>> For example, I believe doing I/O (file I/O, sockets, logging,
>> whatever) in the core of your code isn't necessarily bad design. If
>> you try to split it out, you end up with a complicated -- but
>> unit-testable -- design.

>
> That's where mocking and DI comes in. For example with regard to file
> I/O my C++ functions take streams. You can then set them up with
> string streams during testing.
>
> Unfortunately I've not seen a good way to do this in C so functions
> that do file I/O...only way I've found to test them is to create files
> with the appropriate content, inject the file or FILE*, and delete
> after.


It is pretty simple to interpose I/O library functions in either C or
C++. It is actually more straightforward with C; in C++ if a function
*creates* a file stream to output data, you either have to mock the
whole stream class, or know which lower level functions will be called.
Higher levels of abstraction make for more complex mocks.

> Those are all the hard cases though. They are testable and the
> designs you create to make them so are demonstratively better, but
> they are difficult problems.


No, they are quite simple once you know how!

--
Ian Collins
 
Reply With Quote
 
 
 
 
Jorgen Grahn
Guest
Posts: n/a
 
      10-05-2011
On Mon, 2011-10-03, William Ahern wrote:
> Jorgen Grahn <(E-Mail Removed)> wrote:
>> On Mon, 2011-10-03, nroberts wrote:
>> > On Oct 3, 1:27*pm, James Kuyper <(E-Mail Removed)> wrote:

>> ...
>> >> Testability shouldn't have much affect on your code design. If it does,
>> >> you're doing something wrong, either in your design or your testing.
>> >
>> > I can't say I agree with that at all. One could argue of course that
>> > sure, in fact by definition it is correct since one major bonus of
>> > doing unit testing is that it forces good design, and one main reason
>> > why legacy code in notoriously untestable is because it lacked this
>> > force.

>
>> I partly agree and partly disagree with that. Partly disagree, because
>> there are designs which make perfect sense for the program itself, but
>> are impossible for unit testing.

>
> But being unit testable should be a design goal of most programs. If you
> can't test it to make sure it works, then how do you know if the program
> does what it's supposed to do?


Lack of unit tests doesn't imply lack of testing. You have to spend
more time reviewing the code and on testing on a higher level ("system
testing", or whatever the term is).

I should add here that I think I do more unit testing than most people
around me -- so I'm not *totally* against it.

>> For example, I believe doing I/O (file I/O, sockets, logging,
>> whatever) in the core of your code isn't necessarily bad design. If
>> you try to split it out, you end up with a complicated -- but
>> unit-testable -- design.

>
> Splitting those things out doesn't require complexity, there are just fewer
> ways to do it simply and elegantly (and many more ways to do it poorly).
> Experience and practice will teach you the right way to do it.


Perhaps. I've certainly learned *some* ways of doing it. Some examples
which come to mind:
- make my testable function foo(FILE*) instead of foo(filename)
- or make it a state machine which you feed blocks of data one by one
But I'd rather not do such things unless there are other benefits
apart from testability.

/Jorgen

--
// Jorgen Grahn <grahn@ Oo o. . .
\X/ snipabacken.se> O o .
 
Reply With Quote
 
 
 
 
Ian Collins
Guest
Posts: n/a
 
      10-06-2011
On 10/ 6/11 03:25 AM, Jorgen Grahn wrote:
> On Mon, 2011-10-03, William Ahern wrote:
>> Jorgen Grahn<(E-Mail Removed)> wrote:

>
>>> For example, I believe doing I/O (file I/O, sockets, logging,
>>> whatever) in the core of your code isn't necessarily bad design. If
>>> you try to split it out, you end up with a complicated -- but
>>> unit-testable -- design.

>>
>> Splitting those things out doesn't require complexity, there are just fewer
>> ways to do it simply and elegantly (and many more ways to do it poorly).
>> Experience and practice will teach you the right way to do it.

>
> Perhaps. I've certainly learned *some* ways of doing it. Some examples
> which come to mind:
> - make my testable function foo(FILE*) instead of foo(filename)
> - or make it a state machine which you feed blocks of data one by one
> But I'd rather not do such things unless there are other benefits
> apart from testability.


I'd say your example is such a case. Splitting the work done on the
file from opening it (and all the accompanying error checking baggage)
is good, as well as testable, design.

Whenever I come across a case where something looks difficult to test,
the design can nearly always be improved to make it easier to test.

In other words: tricky to test == design smell.

--
Ian Collins
 
Reply With Quote
 
Nick Keighley
Guest
Posts: n/a
 
      10-06-2011
On Oct 6, 3:56*am, Ian Collins <(E-Mail Removed)> wrote:

> In other words: tricky to test == design smell.


and of all the cute, folksy terms floating around "design smell" must
be the most irritating
 
Reply With Quote
 
Jorgen Grahn
Guest
Posts: n/a
 
      10-11-2011
On Thu, 2011-10-06, Nick Keighley wrote:
> On Oct 6, 3:56*am, Ian Collins <(E-Mail Removed)> wrote:
>
>> In other words: tricky to test == design smell.

>
> and of all the cute, folksy terms floating around "design smell" must
> be the most irritating


Yes. It's subtly anti-intellectual; who wants to smell?

Unfortunately there is also no better term that I can think of.
So I didn't mind Ian using it above.

/Jorgen

--
// Jorgen Grahn <grahn@ Oo o. . .
\X/ snipabacken.se> O o .
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Webinar - Testing the Untestable - Unit Testing Dependencies andLegacy Code (in C++) Avi C Programming 0 06-11-2012 01:55 PM
[ANN] Webinar - Testing the Untestable - Unit Testing Dependenciesand Legacy Code in C++ Avi C++ 0 06-06-2012 11:25 AM
unit-profiling, similar to unit-testing Ulrich Eckhardt Python 6 11-18-2011 02:00 AM
Unit testing errors (testing the platform module) John Maclean Python 1 04-13-2010 02:11 PM
Test::Unit - Ruby Unit Testing Framework Questions Bill Mosteller Ruby 0 10-22-2009 02:02 PM



Advertisments