locked
Help understanding the whole class name space thing. RRS feed

  • Question

  • User-1957783797 posted

    Hi all, Just changing careers and learning C#. I've played around with C, and Swift and know the basics. C# is ok so far but whats holing me back is the name space section. I just can't wrap my head around it. Can somebody here explain it to me like a 1st grader. I watched many youtube videos and I know the "definition" of them, but what are they in terms of the big picture? How to actually use them in a real complete program? Anyone willing to help is greatly appreciated.

    Monday, April 11, 2016 5:42 AM

Answers

  • User-821857111 posted

    First thing to understand is that you don't actually need namespaces. Older versions of Visual Studio never included them in web site templates.

    Their purpose is to provide a way to ring-fence types - to prevent clashes among types with the same name. For example, at some stage you might want to "scrape" the content of a web page and then commit the scraped content to a PDF file. There are two "packages" (open source libraries) that will help you to do that: one is the HtmlAgilityPack and the other is called iTextSharp. They both define a class called "Document", so when you do this with both packages referenced in the same code file:

    var doc = new Document();

    the compiler will have a fit. It will want to know which Document you are trying to create - an HtmlAgililtyPack one or an iTextSharp one? The namespace disambiguates between the two:

    var doc = new HtmlAgilityPack.Document();

    Now it's clear which type you want to instantiate and the compiler is happy.

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Monday, April 11, 2016 10:14 AM
  • User-434868552 posted

    @earleybird36      welcome to forums.asp.net

    unless you're very lucky, you're very late to  be starting a programming career...

    unsolicited free advice is usually worth what one pays for it, sometimes more, often less.  focus as much or more on skills that programmers need to get a job, skills like business knowledge and communications for business application programmers; learning c# is a small part of the picture; your first c# job will be only the beginning of your c# programming career.

    for c#, msdn is one of your very best friends.

    read the articles over and over until you understand them.

       ~~~~~~~~~~~~~~~~~~ 

    "namespace (C# Reference)" https://msdn.microsoft.com/en-us/library/z2kcy19k.aspx 

    excerpts:

    "The namespace keyword is used to declare a scope that contains a set of related objects.

     You can use a namespace to organize code elements and to create globally unique types."

    "Whether or not you explicitly declare a namespace in a C# source file, the compiler adds a default namespace."

    earleybird36, you will be using namespaces all of the time, even though you may not notice.

    the .NET Framework has a multitude of namespaces, study https://msdn.microsoft.com/en-us/library/system(v=vs.110).aspx "System Namespace". 

    also study https://msdn.microsoft.com/en-us/library/dfb3cx8s.aspx "Using Namespaces (C# Programming Guide)".

    excerpt:

    "Namespaces are heavily used within C# programs in two ways.

     Firstly, the .NET Framework classes use namespaces to organize its many classes.

     Secondly, declaring your own namespaces can help control the scope of class and method names in larger programming projects."

    look at .NET Framework source code here:  http://referencesource.microsoft.com/

    example:  System.Web     http://referencesource.microsoft.com/#System.Web,namespaces 

    extract:

    http://referencesource.microsoft.com/#System.Web/Util/SmtpMail.cs,dfe28999206a4371

    /*
     * Simple SMTP send mail utility
     *
     * Copyright (c) 2000, Microsoft Corporation
     */
    namespace System.Web.Mail {
        using System;
        using System.Collections;
        using System.Globalization;
        using System.IO;
        using System.Reflection;
        using System.Runtime.InteropServices;
        using System.Runtime.Serialization.Formatters;
        using System.Security.Permissions;
        using System.Text;
        using System.Web.Hosting;
        using System.Web.Management;
        using System.Web.Util;
    /*
     * Class that sends MailMessage using CDONTS/CDOSYS
     */

    earleybird36namespaces in c# .NET programming are absolutely necessary regardless whether you explicitly specify them.

    BTW, Microsoft has provided a free c# starter course here:

    https://mva.microsoft.com/en-US/training-courses/c-fundamentals-for-absolute-beginners-16169?l=Lvld4EQIC_2706218949 

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Monday, April 11, 2016 11:11 AM

All replies

  • User-821857111 posted

    First thing to understand is that you don't actually need namespaces. Older versions of Visual Studio never included them in web site templates.

    Their purpose is to provide a way to ring-fence types - to prevent clashes among types with the same name. For example, at some stage you might want to "scrape" the content of a web page and then commit the scraped content to a PDF file. There are two "packages" (open source libraries) that will help you to do that: one is the HtmlAgilityPack and the other is called iTextSharp. They both define a class called "Document", so when you do this with both packages referenced in the same code file:

    var doc = new Document();

    the compiler will have a fit. It will want to know which Document you are trying to create - an HtmlAgililtyPack one or an iTextSharp one? The namespace disambiguates between the two:

    var doc = new HtmlAgilityPack.Document();

    Now it's clear which type you want to instantiate and the compiler is happy.

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Monday, April 11, 2016 10:14 AM
  • User-434868552 posted

    @earleybird36      welcome to forums.asp.net

    unless you're very lucky, you're very late to  be starting a programming career...

    unsolicited free advice is usually worth what one pays for it, sometimes more, often less.  focus as much or more on skills that programmers need to get a job, skills like business knowledge and communications for business application programmers; learning c# is a small part of the picture; your first c# job will be only the beginning of your c# programming career.

    for c#, msdn is one of your very best friends.

    read the articles over and over until you understand them.

       ~~~~~~~~~~~~~~~~~~ 

    "namespace (C# Reference)" https://msdn.microsoft.com/en-us/library/z2kcy19k.aspx 

    excerpts:

    "The namespace keyword is used to declare a scope that contains a set of related objects.

     You can use a namespace to organize code elements and to create globally unique types."

    "Whether or not you explicitly declare a namespace in a C# source file, the compiler adds a default namespace."

    earleybird36, you will be using namespaces all of the time, even though you may not notice.

    the .NET Framework has a multitude of namespaces, study https://msdn.microsoft.com/en-us/library/system(v=vs.110).aspx "System Namespace". 

    also study https://msdn.microsoft.com/en-us/library/dfb3cx8s.aspx "Using Namespaces (C# Programming Guide)".

    excerpt:

    "Namespaces are heavily used within C# programs in two ways.

     Firstly, the .NET Framework classes use namespaces to organize its many classes.

     Secondly, declaring your own namespaces can help control the scope of class and method names in larger programming projects."

    look at .NET Framework source code here:  http://referencesource.microsoft.com/

    example:  System.Web     http://referencesource.microsoft.com/#System.Web,namespaces 

    extract:

    http://referencesource.microsoft.com/#System.Web/Util/SmtpMail.cs,dfe28999206a4371

    /*
     * Simple SMTP send mail utility
     *
     * Copyright (c) 2000, Microsoft Corporation
     */
    namespace System.Web.Mail {
        using System;
        using System.Collections;
        using System.Globalization;
        using System.IO;
        using System.Reflection;
        using System.Runtime.InteropServices;
        using System.Runtime.Serialization.Formatters;
        using System.Security.Permissions;
        using System.Text;
        using System.Web.Hosting;
        using System.Web.Management;
        using System.Web.Util;
    /*
     * Class that sends MailMessage using CDONTS/CDOSYS
     */

    earleybird36namespaces in c# .NET programming are absolutely necessary regardless whether you explicitly specify them.

    BTW, Microsoft has provided a free c# starter course here:

    https://mva.microsoft.com/en-US/training-courses/c-fundamentals-for-absolute-beginners-16169?l=Lvld4EQIC_2706218949 

    • Marked as answer by Anonymous Thursday, October 7, 2021 12:00 AM
    Monday, April 11, 2016 11:11 AM
  • User303363814 posted

    I'll be radical.  There is no such thing as namespaces!

    If you ever have the misfortune to look at the Intermediate Language that the compiler generates from your source code you will see that there is no such thing as a namespace.

    The name of every class is purely a series of characters.  For example, the 'int' that you are used to is really 'System.Int32', the Timer class that you might use is either 'System.Timers,Timer' or 'System.Threading.Timer'.  The actual name is a string which has 'dots' in it.

    Typing those long names in your code is a pain in the neck.  To help you out the compiler allows you to specify these 'namespace' things.  When you have a 'using' statement in effect then the compiler tries to help you out by attaching the string that the 'using' statement specifies, followed by a 'dot' to the front of any class name that you specify.  If it finds a match with any referenced assemblies then it assumes that it has worked out what you meant.

    So, if you say

    using System;

    Then in your code you can say

    Int32 x;

    and the compiler will work out that you mean

    System.Int32 x;

    or if you have the same 'using' statement in effect and you say

    Threading.Timer myTimer;

    That you mean

    System.Threading.Timer myTimer;

    An alternative would be to add another using and declare your variable as

    using System;
    using System.Threading;
    Timer myTimer;

    With this code, the compiler first look to see if 'System.Timer' exists in any referenced assembly (because of the first 'using' statement) and find that it does not.  Then it would look for 'System.Threading.Timer' because of the second using and it should succeed if you have referenced the required assembly.  If these are the only using statements in your source file then all is good.  If there are other 'using' statements, then the compiler would keep looking using all the 'using' statements and if it succeeds more than once then an error is emitted.

    For example,

    using System;
    using System.Threading;
    using System.Timers;
    Timer myAmbiguousTimer;

    would fail because the compiler would find both 'System.Threading.Timer' and 'System.Timer.Timer'.  You would need some extra code to help the compiler understand which particular variety of 'Timer' you wanted.

    Monday, April 11, 2016 11:48 AM
  • User-434868552 posted

    @PaulTheSmith

    PaulTheSmith

    There is no such thing as namespaces!

    incorrect

    namespace NameSpacesMatter
    {
        class Program
        {
            static void Main(string[] args)
            {
            }
        }
    }

    Build output (visual studio community 2015):

    ========== Build: 1 succeeded, 0 failed, 0 up-to-date, 0 skipped ==========
    
    //  namespace NameSpacesMatter
    {
        class Program
        {
            static void Main(string[] args)
            {
            }
        }
    }

    Like above, but with the first line commented out, Build output (visual studio community 2015):

    Line 2   Error code CS1022   Type or namespace definition, or end-of-file expected
    Line 9   Error code CS1022   Type or namespace definition, or end-of-file expected

    Without the namespace in the small program above, the code will not compile.

    A second example:

    namespace NameSpacesMatter
    {
        class Program
        {
            static void Main(string[] args)
            {
                System.Console.WriteLine("PaulTheSmith");
                TimeTeller.ThisWorks.WriteLine();
            }
        }
    }
    
    namespace TimeTeller
    {
       public class ThisWorks
       {
           public static void WriteLine()
           {
                System.Console.WriteLine(System.DateTime.Now);
           }
        }
    }

    The above version compiles with no errors; here is the output.

    PaulTheSmith
    2016-04-11 13:33:40

    Here is the assembler code during debug:

                System.Console.WriteLine("PaulTheSmith");
    00873303  mov         ecx,dword ptr ds:[339230Ch]  
    00873309  call        73CFD4B0  
    0087330E  nop  
                TimeTeller.ThisWorks.WriteLine();
    0087330F  call        00870D28 

    Even though you do not see assembler code for the namespace, it's obvious that the c# compiler has used the namespace information to call the correct methods.

    EDIT:

    If you ever have the misfortune to look at the Intermediate Language that the compiler generates from your source code you will see that there is no such thing as a namespace.

    again, incorrect

    (a) looking at IL is an excellent way to deepen one's understand of c#

    (b) here's partial IL for the second program above:

    .method private hidebysig static void  Main(string[] args) cil managed
    {
      .entrypoint
      // Code size       19 (0x13)
      .maxstack  8
      IL_0000:  nop
      IL_0001:  ldstr      "PaulTheSmith"
      IL_0006:  call       void [mscorlib]System.Console::WriteLine(string)
      IL_000b:  nop
      IL_000c:  call       void TimeTeller.ThisWorks::WriteLine()
      IL_0011:  nop
      IL_0012:  ret
    } // end of method Program::Main

    as you can see from the IL, the namespace is explicitly used.

    even if i add 2 usings at the top of the second program:

    using System;
    using TimeTeller;

    and modify these two lines:

                Console.WriteLine("PaulTheSmith");
                ThisWorks.WriteLine();

    the IL is the same because IL needs to keep track of the appropriate namespace..

    https://msdn.microsoft.com/en-us/library/f7dy01k1(v=vs.110).aspx "ildasm.exe (IL Disassembler)"

    END EDIT.

    Monday, April 11, 2016 5:40 PM
  • User303363814 posted

    the code will not compile

    You do not have a valid C# source file.  A c# source file cannot start with a '{' character.  Remove the outer pair of curly braces and your program compiles and runs just fine, no need for any 'using' statements or 'namespace declarations.  (No program needs 'using' or 'namespace' statements.  They are a great convenience and provide yummy syntactic sugar which I really like.  But they are not needed.)

    as you can see from the IL, the namespace is explicitly used

    Where?  All I see are the names of two classes

    1) System.Console

    2) TimeTeller.ThisWorks

    Monday, April 11, 2016 11:23 PM
  • User-434868552 posted

    @PaulTheSmith

    PaulTheSmith

    A c# source file cannot start with a '{' character.

    actually, it appears that you are correct here ... below i'm referencing the "c# Language Specification 5.0".

    From §2.2.2 Lexical grammar, this sentence appears to imply that one can start with a '{' because a '{' is a token:

    "Every source file in a C# program must conform to the input production of the lexical grammar (§2.3)."

    §2.4 Tokens include punctuators and '{' is a punctator [§2.4.5 Operators and punctuators]

    However, §9. Namespaces begins "C# programs are organized using namespaces."

    §9.1 Compilation units:  "A compilation-unit defines the overall structure of a source file." 

    compilation-unit:

    extern-alias-directivesopt using-directivesopt global-attributesopt

    namespace-member-declarationsopt

    "namespace-member-declarations of each compilation unit of a program contribute members to a single declaration space called the global namespace"

    So, although '{' is a token, it does not contribute a member ... that is possibly why the compiler rejects the  beginning '{'.

    However, the namespace-member-declarations are optional ~~ for that reason, perhaps the compiler should allow an intial '{'.

        ~~~~~~~~~~~~~~~~~~~~~~~~~~

    for this trivial program, there is likely a single unnamed namespace, i.e., the so called global namespace:

    class Program
    {
        static void Main(string[] args)
        {
        }
    }

    IL:

    .method private hidebysig static void  Main(string[] args) cil managed
    {
      .entrypoint
      // Code size       2 (0x2)
      .maxstack  8
      IL_0000:  nop
      IL_0001:  ret
    } // end of method Program::Main 

    HOWEVER, there is the class named Program ... as a class it needs a constructor, so lets look at the IL of the default construtor:

    .method public hidebysig specialname rtspecialname 
            instance void  .ctor() cil managed
    {
      // Code size       8 (0x8)
      .maxstack  8
      IL_0000:  ldarg.0
      IL_0001:  call       instance void [mscorlib]System.Object::.ctor()
      IL_0006:  nop
      IL_0007:  ret
    } // end of method Program::.ctor

    PaulTheSmith, as you can see, the System namespace is required even for such a trivial program.

    PaulTheSmith

    Where?  All I see are the names of two classes

    1) System.Console

    2) TimeTeller.ThisWorks

    PaulTheSmith

    1) Console is a class that is a member of the System namespace

    2) ThisWorks is a class that is a member of the TimeTeller namespace

    PaulTheSmith

    No program needs 'using' or 'namespace' statements.

    incorrect

    Proof:  a single program the uses one or more of .Create() methods below can not AFAIK be written without specifying their respective namespace:

    https://msdn.microsoft.com/en-us/library/system.data.entity.database.create(v=vs.113).aspx "Database.Create Method ()"

    https://msdn.microsoft.com/en-us/library/system.io.file.create(v=vs.110).aspx "File.Create Method"

    https://msdn.microsoft.com/en-us/library/system.net.webrequest.create(v=vs.110).aspx  "WebRequest.Create Method"

    https://msdn.microsoft.com/en-us/library/system.xml.xmlwriter.create(v=vs.110).aspx "XmlWriter.Create Method"

    EDIT:

    this code generates an interesting compiler error (note that there is no namespace keyword):

    static void Main(string[] args)
    {
    }

    the error is:

    ------ Build started: Project: NameSpacesMatter, Configuration: Debug Any CPU ------
    error CS0116: A namespace cannot directly contain members such as fields or methods
    ========== Build: 0 succeeded, 1 failed, 0 up-to-date, 0 skipped ==========

    so the c# compiler treats the source file as if it is a namespace!  (because it is the global namespace)

    END EDIT.

    Tuesday, April 12, 2016 1:43 AM
  • User303363814 posted

    actually, it appears that you are correct

    Thank you for your condescension. Does 'appears' mean that I am right and you are not?

    as you can see, the System namespace is required even for such a trivial program.
    I do not see.  I do not see anywhere in your code that a 'using' or 'namespace' statement is required.  (I can't actually see that you have a 'using' or 'namespace' statement - so your example seems to show the reverse of what you are trying to prove)

    Console is a class that is a member of the System namespace
    The full name of the class is System.Console

    incorrect

    Proof:  a single program the uses one or more of .Create() methods below can not AFAIK be written without specifying their respective namespace:

    Again, you give further examples that 'using' and 'namespace' statements are entirely optional.  Why do you keep proving my point?  I showed examples with the System.Timers.Timer and System.Threading.Timer - thank you for the extra examples proving my point. 

    interesting compiler error
    It is true that syntactically incorrect files give compiler errors .  You cannot declare a method outside of a class, so what?

    As I said before 'using' and 'namespace' statements provide fantastic syntactic sugar and I wouldn't want to work without them.  Sometimes they get in the way as with the examples I have shown and the further examples that you showed to back me up.  Just because 'using' and 'namespace' statements do not always make it easier to write code does not mean they should be abandoned.  The statements are useful but understanding that they just create a helpful fiction (albeit a fiction that is widely documented and used and works fantastically in practice and is even mentioned in compiler error message) helps when you bump into the corner cases.

    Tuesday, April 12, 2016 7:19 AM
  • User-434868552 posted

    @PaulTheSmith

    Thank you for your condescension. Does 'appears' mean that I am right and you are not?

    PaulTheSmith, i regret you think that i was patronizing you, i was not; FWIW i try to choose my words carefully ~~ by "appears" i meant that although i thought you were correct, i had yet to fully understand why based on wading through the "c# Language Specification 5.0".

    Now, Jon Skeet's answer to "can a c# program start with a '{'; if not, why not?" confirms not only that you are correct that a c# program can not begin with a '{' but also clarifys why.

    gerrylowry

    as you can see, the System namespace is required even for such a trivial program.

    I do not see.  I do not see anywhere in your code that a 'using' or 'namespace' statement is required.  (I can't actually see that you have a 'using' or 'namespace' statement - so your example seems to show the reverse of what you are trying to prove)

    PaulTheSmith just because you do not see namespace in my source code does not validate your claim that namespace is not required.  The IL explicitly demonstrates that the System namespace is essential to construct an instance of the class Program.

    see "Object Classhttps://msdn.microsoft.com/en-us/library/system.object(v=vs.110).aspx 

    =====> Namespace: System
                    Assembly: mscorlib (in mscorlib.dll)

    System.Object can not exist without having a namespace System.

    PaulTheSmith, look at the Reference Source for the Object class in the System namespace, especially these two lines found here:
                            http://referencesource.microsoft.com/#mscorlib/system/object.cs 

    namespace System {
    public class Object

    Console is a class that is a member of the System namespace

    The full name of the class is System.Console

    The name of the class is Console; the disambiguated name prepends the namespace System.

    see http://referencesource.microsoft.com/#mscorlib/system/console.cs 

    namespace System {
       public static class Console

    you give further examples that 'using' and 'namespace' statements are entirely optional.

    PaulTheSmithyou are not even able to code a program that uses the class Console without in some way specifying the namespace System.

    Do you deny MSDN?

    "Namespaces (C# Programming Guide)  https://msdn.microsoft.com/en-CA/library/0d941h9d.aspx 

    "System is a namespace and Console is a class in that namespace.

     The using keyword can be used so that the complete name is not required, ..."

    There is no such thing as namespaces!

    PaulTheSmith, your statement "There is no such thing as namespaces" is 100% wrong.  MSDN, as shown above acknowledges the existence of namespaces.

    As I said before 'using' and 'namespace' statements provide fantastic syntactic sugar and I wouldn't want to work without them.

    "Namespace Statement"

     https://msdn.microsoft.com/en-us/library/0dx91cw5.aspx 

    in a trivial program, you can avoid having a Namespace Statement but you can not avoid explicitly referencing namespaces.

    PaulTheSmith, this program does not compile without errors:

    class Program
    {
        static void Main(string[] args)
        {
            Int32 integer = 1234;
        }
    }

    PaulTheSmith, by making the above trivial program compile clean, you would disprove your statement "There is no such thing as namespaces".

    FWIW 

    Tuesday, April 12, 2016 9:03 AM
  • User303363814 posted

    I am sure that explaining this to you is beyond my powers.

    I skipped to the end of your post and saw

    this program does not compile without errors:
    Ummm ... if it doesn't compile then it is not a program.  Sorry to state the obvious but I guess it is needed.

    The easy way to change your text file so that it becomes a program is to change the characters 'Int32' to 'System.Int32'.  Bingo! Instant program - no 'using' statement, no 'namespace' statement.

    If this is not clear then there is little point in replying because I cannot possibly make it any simpler than this.

    Tuesday, April 12, 2016 10:17 AM
  • User-434868552 posted

    @earleybird36

    F.Y.I.  The following statement, addressed above, is 100% wrong.

    There is no such thing as namespaces

    F.Y.I.:  The following statement, to be addressed below, is misleading.

    you don't actually need namespaces

    earleybird36, i strongly recommend that you become very familiar with the "c# language specification 5.0"(a, b, c).

    The "c# language specification 5.0"(c) is 511 pages.

    study "Chapter 9 Namespaces", pp. 262-271,

    additionally, see the following sections:

    3. Basic concepts
        3.4.1 Namespace members
        3.8    Namespace and type names
        3.8.1  Fully qualified names

    B. Grammar
        B.2.6  Namespaces

    earleybird36, study this too:  "Using Namespaces (C# Programming Guide)"  https://msdn.microsoft.com/en-us/library/dfb3cx8s.aspx 

    excerpt:

    "Namespaces are heavily used within C# programs in two ways.

     Firstly, the .NET Framework classes use namespaces to organize its many classes.

     Secondly, declaring your own namespaces can help control the scope of class and method names in larger programming projects."

    earleybird36, to succeed in your career change and become a c# programmer, you will need to understand and use namespaces.

    (a) "C# Reference"  https://msdn.microsoft.com/en-us/library/618ayhy6.aspx 

    (b) "C# Language Specification"  https://msdn.microsoft.com/en-us/library/ms228593.aspx 

    (c) "C# Language Specification 5.0"  download:  https://www.microsoft.com/en-us/download/details.aspx?id=7029 

    Tuesday, April 12, 2016 6:28 PM
  • User-821857111 posted

    F.Y.I.:  The following statement, to be addressed below, is misleading.

    you don't actually need namespaces

    OK - to clarify: you can build a perfectly good ASP.NET site without ever declaring a namespace.

    Tuesday, April 12, 2016 8:54 PM