• Johnie (unregistered)

    Biggest abomination of VB is the lack of strict types and operations.

    Take this one: Left(frac, 2) + 1
    That's a [string] + [int] --> [string]
    And because of the + sign, it converts the first string to an int.

    Anyways, this one isn't as bad as some of the other WTFs

  • TJ (unregistered)

    Im proud to say I dont know WTF this code is doing because I never had to touch access. I dont even want to know what the Fix Method does.

  • Bu (unregistered)

    Ummm... I'm not VB-literate so I may be off here, but isn't this guy just trying to do something like...

    Function roundoff(x)
    roundoff = Int((x * 100) + .5) / 100
    End Function

    This is clearly a case of someone who should never have been allowed near a computer. Heck, near anything electric for that matter!

  • TheF0o1 (unregistered)

    What the frac?

    Yet another example of how numeric operations are much harder to do with strings. Heh, that "-0" reminds me of the bogus bug reports that used to circulate around my workplace on April 1.

  • Alex Papadimoulis (unregistered)

    Bu has successfully replaced the entire function code with a single line. Good job!

  • TheF0o1 (unregistered)

    LOL! I just looked up the Fix function in MSDN library. It "Returns the integer portion of a number". But the funniest part is that at the bottom of the page it says, "See also... Round Function". How many of us here know how to RTFM?

  • df (unregistered)

    I haven't looked at this code enough to say anything about it specifically, but I can tell you from experience, don't throw stones at something like this just because there was already a function to do it. I've had to write special rounding functions before to match legacy systems that had rounding errors. (I am not making this up). Microsoft has a pretty standard rounding method now, but in the old days, different MS languages and apps had subtle differences in their rounding function.

  • Bu (unregistered)

    ROFL TheF0o1 that's a good one!

  • Cakkie (unregistered)

    OMG, someone shoot this person. Why do something the easy way when there's a hard way :p

    A very very very interesting piece of code are these two lines, when dealing with negative numbers.

    LenFrac = Right(frac, Len(frac) - 1)
    If Len(LenFrac) = 2 Then

    He first assigns all but 1 character to the integer LenFrac, basically stripping the - sign. Then he does a Len() on the integer. The thing is, Len accepts a variant, not a string. Therefore, the length of the integer is returned rather than the length of the string the integer represents. This means that no matter what value LenFrac has, Len() will always return 2 (since an integer is 2 bytes). This means that he will insert another -0 in front of the number, giving him a value that is 1/10 of what it should be :p

  • Bu (unregistered)

    Tell the truth, df, you're the author of this abomination aren't you? LOL!

  • Manni (unregistered)

    I only did a little testing on this code because otherwise the little man inside my computer would have come out and shot me...

    I compared this to the Round() function built-in to VB and it returned the EXACT same value as this convoluted atrocity of a Function. To hell with replacing it with a single line, how about with a feature found in VB by default:

    Round(x, 2)

    What are the situations where this WON'T work?

  • Bu (unregistered)

    Hey, I did say I was VB-challenged, but apparently not NEARLY as challenged as the author of this hideousness.

    "The horror... The horror..."

  • Dz (unregistered)

    Maybe this guy was getting ready to convert to .NET :
    http://weblogs.asp.net/sfurman/archive/2003/03/07/3537.aspx

  • Dz (unregistered)

    </sarcasm>

  • Bill Gates (unregistered)

    My software was not intended to be coded in this fashion... Please take a computer class.
    -Bill

  • Centaur (unregistered)

    There was once a project I worked on that at one time had a function that basically returned a string representation of 1 + x, given a string representation of x, in a convoluted (and incorrect) way. Mind you, the code was in Delphi which has an integer type and everything necessary to convert between strings and integers.

  • Hassan Voyeau (unregistered)

    "What are the situations where this WON'T work? "

    Manni : try -0.1 it returns -0.01 as pointed out Cakkie.

  • Eric W. Bachtal (unregistered)

    Bu - You're one-liner needs a CStr() call in order to match the original's expected string output. ;)

    Manni - The VBA Round() method does banker's rounding, which the misguided author of roundoff probably didn't want. So, given 1.135, both routines will return 1.14 (assuming a second parameter of 2 to Round()), but given 1.145, Round() will return 1.14 while roundoff() (or Bu's one-liner) will return 1.15.

  • Nick D (unregistered)

    What you want is the FormatNumber(number, X) function. This rounds a number to X decimal places AND returns it as a string into the bonus!

  • Jeff S (unregistered)

    (I'm the lucky guy who found this)

    The whole function is just wonderful, but my favorite part is this:

    Result = Fix(x) + frac

    Look at that carefully ... Result is a string, Fix() returns a numeric value, and frac is a string ... what does this do? Concatenation? Addition? Who knows !?

    Just a work of art!

  • Manni (unregistered)

    Hassan: I think you misunderstood me. Round() will return -0.1 if you pass -0.1 to it. I hope you mean that this guy's function screwed it up and returned -0.01.

    Eric B.: I knew I remembered something funky about Round(). Thanks for letting me know. I swear I don't see the point of rounding to the nearest even number, there's gotta be some logic behind it though.

  • Steve O. (unregistered)

    Rounding the nearest even number helps make it a wash to round. If you always rounded up, everything would be off to the high side. By rounding to the nearest number, it keeps rounding from skewing the numbers.

  • Cakkie (unregistered)

    @Jeff S: just for the record, if there are any numeric datatypes involved, VB will always perform an Addition. Only when both are strings, a concatination is done. Since Fix always returns a number (unless Null is passed, in which case Null is returned), an addition will be used in this case.

    "123" + "4" => "1234" -> two strings
    "123" + 4 => 127 -> 1 string, 1 number
    Fix("123.456") + "4" => 127 -> Fix returns a number

  • XTOCb (unregistered)

    If Fix(x) is an integer value, and frac is a string representing a value between 0 and 1, then it doesn't matter whether the plus sign does concatenation or addition :)

  • Thomas Eyde (unregistered)

    I have seen situations where rounding to the even number did not achieve what's meant to be. Coincidentily, it also happened in Access.

    I had to share a certain number among 8 stakeholders, but when I added the numbers up again, I was always missing the .02.

    You need a large number to justify Banker's rounding.

  • Thomas Eyde (unregistered)

    In all fairness to VB, it has a decent type system, but you have to declare your types to get the advantage:

    dim theNumber as double

  • gary longstaff (unregistered)

    I agree

  • (unregistered) in reply to XTOCb
    XTOCb: it doesn't matter only for positive numbers. If Fix(x) is negative, then addition will increase it, and concatenation decrease.  :-)
  • (cs)

    Sigh. See http://c2.com/cgi/wiki?FloatingPointCurrency and http://c2.com/cgi/wiki?FloatingPointFractions .

    Currency should always be held in a fixed-point decimal. If you don't have that, store it as an integer holding the number-of-cents. And use variable names that remind you:

    [code language="javascript"]
        int UserPaymentCents
    int PaidAmountMinutes[/code]
  • Den Raskovalov (unregistered)

    ??/??

    ??????, ???? ????

  • kvas (unregistered) in reply to Den Raskovalov

    ????? ????, ???? ???!

  • Den Raskovalov (unregistered)

    Function roundoff2(ByVal x As Double)
        If x > 0 Then
            roundoff2 = Fix(x * 100 + 0.5) / 100
        Else
            roundoff2 = -Fix(-x * 100 + 0.5) / 100
        End If
    End Function

  • (cs) in reply to Den Raskovalov
    Anonymous:
    Function roundoff2(ByVal x As Double)
        If x > 0 Then
            roundoff2 = Fix(x * 100 + 0.5) / 100
        Else
            roundoff2 = -Fix(-x * 100 + 0.5) / 100
        End If
    End Function


    I'm tempted to say...
    Function roundoff2(ByVal x As Double)
        If x >= 0 Then
            roundoff2 = Fix(x * 100 + 0.5) / 100
        Else
            roundoff2 = -roundoff2(-x)
        End If
    End Function
  • Calculator Ftvb (unregistered)

    I've done some programming in both VB and VB.Net (more in VB.Net), but given my knowledge of them, this function (or "WhatTheFunction" :-)) is just atrocious, and must have a better (shorter, easier, faster, etc.) alternative!

  • Brian (unregistered)

    This article was referenced by Raymond Chen in his discussion of this similar WTF code: http://blogs.msdn.com/oldnewthing/archive/2005/01/26/360797.aspx

Leave a comment on “Well ... that's one way to Roundoff ...”

Log In or post as a guest

Replying to comment #:

« Return to Article