Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people, just like you, are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
Solved

Where to put enumerations?

Posted on 2011-09-09
13
200 Views
Last Modified: 2012-05-12
I have an SMTP class which sets the following property

 Public Property SmtpSAuthenticationType() As AuthenticationTypeException.AuthenticationType
        Get
            Return _smtpSAuthenticationType
        End Get
        Set(ByVal value As AuthenticationTypeException.AuthenticationType)
            Try
                If Not [Enum].IsDefined(GetType(AuthenticationTypeException.AuthenticationType), value) Then
                    Throw New AuthenticationTypeException
                End If
                _smtpSAuthenticationType = value
            Catch ex As Exception
                _errors.Add("SMTP Server Authentication Type", ex.Message)
            End Try
        End Set
    End Property

I have defined the enumeration in the exception, should it be in the class instead?
0
Comment
Question by:rocky050371
  • 7
  • 6
13 Comments
 

Author Comment

by:rocky050371
ID: 36509633
As an addition to that if I am using a flags enumeration should they be decalred in the same place too
0
 
LVL 75

Expert Comment

by:käµfm³d 👽
ID: 36510186
This:

If Not [Enum].IsDefined(GetType(AuthenticationTypeException.AuthenticationType), value) Then

Open in new window


doesn't really benefit you. You have defined the type of SmtpSAuthenticationType to be AuthenticationTypeException.AuthenticationType, so anybody using your code is restricted to assigning values of that type--otherwise a compiler error is generated. The only reason I could think to have code like this is if your property were being assigned via reflection, but I believe even then, an error would occur (a runtime error) due to trying to assign an inappropriate value.

I have defined the enumeration in the exception, should it be in the class instead?
I believe MS suggests enums get their own code file, although they seem to have done a good job of creating enums and other classes inside of other classes, themselves! Put your enum wherever it is the most logical. To me, including the enum inside of the AuthenticationTypeException class seems a bit counter-intuitive.
0
 

Author Comment

by:rocky050371
ID: 36510280
there is a try block around it, surely checking whether the value is defined within the enumeration provides feedback to those who are consuming the business object
0
Master Your Team's Linux and Cloud Stack

Come see why top tech companies like Mailchimp and Media Temple use Linux Academy to build their employee training programs.

 

Author Comment

by:rocky050371
ID: 36510286
or in fact should I set the property to an integer then check it within the assignment?
0
 
LVL 75

Expert Comment

by:käµfm³d 👽
ID: 36510638
You're missing what I'm saying. The type of value inside your set will ALWAYS be AuthenticationTypeException.AuthenticationType. The compiler won't allow you to pass in "cat", 1, new Boat(), etc. You always have to assign a value of type AuthenticationTypeException.AuthenticationType to the SmtpSAuthenticationType member. In other words:

Good
obj.SmtpSAuthenticationType = AuthenticationTypeException.AuthenticationType.FirstEnumMember
obj.SmtpSAuthenticationType = DirectCast(1, AuthenticationTypeException.AuthenticationType)

Open in new window


Bad
obj.SmtpSAuthenticationType = "cat"
obj.SmtpSAuthenticationType = 1
obj.SmtpSAuthenticationType = new Boat()

Open in new window



Note, the difference between #2 Bad and #2 Good is that the good version has an explicit cast. This is assuming you don't have Option Strict set to Off.
0
 

Author Comment

by:rocky050371
ID: 36510794
I appreciate what you are saying, but to cater for any value being passed in is it better then for calling object to treat the public property as an integer then cast it to the enum for internal use?
0
 
LVL 75

Expert Comment

by:käµfm³d 👽
ID: 36511444
but to cater for any value being passed in is it better then for calling object to treat the public property as an integer then cast it to the enum for internal use?
If you were to change the type of SmtpSAuthenticationType to int, then you would want the if logic, because int can hold many more values than what you would probably define in your AuthenticationType enum. The benefit of using an enum over an int is that your range of valid values is restricted to only those defined by the enum; if you use an int, then your possible values become -2147483648 to 2147483647, but you enum may only define 1 to 5. This is why you would want a check like what you have--to weed out the other 4294967291 values that don't correspond to a valid enum value. If you keep the enum as the type of your SmtpSAuthenticationType property, then you avoid having to check for these unacceptable values.
0
 

Author Comment

by:rocky050371
ID: 36511507
but this then  relies on the calling program to know that the public property only accepts a value within the allowed range.

How would you deal with this?

Presumably if I am right in thinking that removing he enum check is also effectively removing the business rule




0
 
LVL 75

Expert Comment

by:käµfm³d 👽
ID: 36511647
It looks like I might be eating crow after this conversation  : \

In testing my assertions, it seems that VB is a tad more "forgiving" than C# is, even though we're still playing in .NET land. Passing in a casted value to an a field/property of type enum will still allow you to store the value without error--C# would not allow this. For example:

Module Module1

    Sub Main()
        Dim x As AuthenticationType = 1700

        Console.WriteLine(x.ToString())
        Console.ReadKey()
    End Sub

End Module

Public Enum AuthenticationType
    FirstEnumMember = 1
End Enum

Open in new window


I've only defined one enum member: FirstEnumMember. Its value is 1. However, in my test code, I am casting the value of 1700 to the enum's type. The assignment will succeed, but when the ToString call hits, you will simply see the value 1700 rather than the default of the enum member's name--if you assigned the value of FirstEnumMember to the variable x, the ToString call would print "FirstEnumMember" and not "1".

Based on this test, you are correct in your logic for the property. If you ever switch to C#, you shouldn't need such logic  = )
0
 

Author Comment

by:rocky050371
ID: 36511679
:-)

I would still be interested to know how you would do it, would you always just force consumers to pass a correct range value in, or would you switch it to an int etc


0
 
LVL 75

Expert Comment

by:käµfm³d 👽
ID: 36511785
I would use an enumeration because it associates friendly names with values. It much easier to remember:

Public Enum LampState
    Off = 0
    On = 1
End Enum

than it is to remember:

obj.LampState = 1  ' Lamp is on

Open in new window


especially since Intellisense will pop up and list "Off" and "On" as possible values when using an enumeration.

In reality, enumerations are integer values under the hood anyway, so when using an enum, you are still using an int--you just get a friendly name associated with the value.
0
 
LVL 75

Expert Comment

by:käµfm³d 👽
ID: 36511791
Correction to my first example (to make it more in line with the second:

Public Enum LampState
    Off = 0
    On = 1
End Enum

Open in new window


obj.LampState = LampState.Off

Open in new window

0
 
LVL 75

Accepted Solution

by:
käµfm³d   👽 earned 500 total points
ID: 36511810
Another benefit to using enumerations is that if the value of any particular enum member ever needs to change, then you can simply change it in the definition of the enum rather than searching for every spot where you used a "1" in code. So my last example could be:

Public Enum LampState
    Off = 2  ' The boss decided that 2 makes more sense as an "off" value
    On = 1
End Enum

Open in new window


Now our other code doesn't need to be changed:

obj.LampState = LampState.Off

Open in new window


because we simply changed the definition.
0

Featured Post

Master Your Team's Linux and Cloud Stack!

The average business loses $13.5M per year to ineffective training (per 1,000 employees). Keep ahead of the competition and combine in-person quality with online cost and flexibility by training with Linux Academy.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
Import Data from Multiple Text Files in Excel 12 60
JSON  parse help 7 40
SSRS 2016 Rendering HTML tables 3 26
Convert Ctime to date time in textfile? 7 31
The ECB site provides FX rates for major currencies since its inception in 1999 in the form of an XML feed. The files have the following format (reducted for brevity) (CODE) There are three files available HERE (http://www.ecb.europa.eu/stats/exch…
This article shows how to deploy dynamic backgrounds to computers depending on the aspect ratio of display

856 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question