Table of Contents

Interface ICodeContainer

Namespace
NDepend.CodeModel
Assembly
NDepend.API.dll

Represents a code element that can contain executable code. This interface is implemented by IMethod, IType, INamespace, IAssembly and ICodeBase.

public interface ICodeContainer : IUser, ICodeElement, IUsed
Inherited Members
Extension Methods

Remarks

This interface implements IUser because ICodeContainer contains executable code per definition, and executable code can used code elements.
A ICodeContainer object doesn't necessarily contain executable code. For example an abstract method object, is a IMethod, that is a ICodeContainer, yet an abstract method doesn't contain executable code.

Properties (12)

CoverageDataAvailable

Gets a boolean value that indicates if coverage data is available for this code element.

bool CoverageDataAvailable { get; }

Property Value

bool
  • false if no code coverage data are imported through the NDepend project settings IProjectCoverage.
  • false if this code element is defined in a third-party assembly.
  • false if the PDB file of this assembly or code element parent's assembly, hasen't been found.
  • false if the code element is tagged with an attribute that excludes elements from coverage statistics.
  • false if the code element does not contain any PDB sequence point.
  • else returns true.
    This property returned boolean flag is the inverse value of IsExcludedFromCoverage.
    See Also

    ExcludedFromCoverageStatistics

    Gets a value indicating whether this assembly, namespace, type or method is explicitly excluded from coverage.

    bool ExcludedFromCoverageStatistics { get; }

    Property Value

    bool

    Remarks

    This property returns true for code elements matched by the <CodeCoverage> exclusion section within the .runsettings file provided (if any).
    No matter the coverage technology used, methods and types tagged with 'System.Diagnostics.CodeAnalysis.ExcludeFromCodeCoverageAttribute' are excluded from coverage statistics.
    For the VS coverage technology, tagging a method or a type with 'System.Diagnostics.DebuggerNonUserCodeAttribute' or 'System.Diagnostics.DebuggerHiddenAttribute' exclude it also from coverage statistics.
    You can also specify a custom attribute to excluded elements from coverage statistics in the Project Propeties > Analysis > Coverage > Settings form.
    Unlike the property IsExcludedFromCoverage, this property returns false for code elements whose coverage data is not available in coverage files provided - but that are not explicitly excluded from coverage.

    See Also

    HalsteadVolume

    Gets a numeric value measuring this element Halstead Volume.

    uint? HalsteadVolume { get; }

    Property Value

    uint?

    null if this code element is defined in a third-party assembly.
    Otherwise, returns the Halstead Volume for this code element.

    Remarks

    The Halstead Volume (HV) quantifies the amount of information contained in a method based on its operators and operands.
    It is defined as V = N × log₂(n), where N is the total number of tokens (N = N₁ + N₂, with N₁ the number of operator occurrences and N₂ the number of operand occurrences) and n is the vocabulary size (n = n₁ + n₂, with n₁ distinct operators and n₂ distinct operands).
    The value is computed from the IL code to ensure language neutrality. IL instructions that act on control flow, arithmetic, logical, comparison, assignment, object creation and method invocation are counted as operators. Identifiers (locals, parameters, fields, properties treated as values), and literal constants (numeric, string, char, bool, null) are counted as operands.
    Property getters/setters, indexers and event add/remove are treated as calls (operators). Generic instantiations and boxing/unboxing contribute via their emitted IL operations. Short-circuit boolean operations and compound assignments contribute via their underlying IL instructions. Declarations do not add operands unless a symbol is referenced; unused parameters therefore do not increase counts.
    Recommendations:
    Methods with a Halstead Volume below 150 are usually simple; values between 150 and 400 are moderate. Methods with a Halstead Volume above 800 indicate high cognitive load and should be simplified or split (except if they are automatically generated by a tool).
    Types with a Halstead Volume below 800 are generally simple. Volumes between 800 and 3,000 indicate moderate complexity. Types with a Halstead Volume above 8,000 are very complex and should be refactored into smaller, more cohesive types. High volumes often suggest a violation of the Single Responsibility Principle or a concentration of unrelated logic in one type.

    IsExcludedFromCoverage

    Gets a value indicating whether this assembly, namespace, type or method don’t have associated coverage data.

    bool IsExcludedFromCoverage { get; }

    Property Value

    bool

    Remarks

    This property returns:

  • true if no code coverage data are imported through the NDepend project settings IProjectCoverage.
  • true if this code element is defined in a third-party assembly.
  • true if the PDB file of this assembly or code element parent's assembly, hasen't been found.
  • true if the code element is tagged with an attribute that excludes elements from coverage statistics.
  • true if the code element does not contain any PDB sequence point.
  • else returns false.
    This property returned boolean flag is the inverse value of CoverageDataAvailable.
    Unlike the property ExcludedFromCoverageStatistics, this property also returns true for code elements whose coverage data is not available in coverage files provided - but that are not explicitly excluded from coverage.
    See Also

    MaintainabilityIndex

    Gets a numeric value measuring this element Maintainability Index.

    byte? MaintainabilityIndex { get; }

    Property Value

    byte?

    null if this code element is defined in a third-party assembly.
    Otherwise, returns the Halstead Volume for this code element.

    Remarks

    The Maintainability Index (MI) is a composite metric defined by Microsoft to estimate how easy it is to maintain a method, a class, a namespace, a project or an application.
    It is derived from three main measures: HalsteadVolume, CyclomaticComplexity, and NbLinesOfCode. The formula is:
    MI = MAX(0, (171 - 5.2 × log(HV) - 0.23 × CC - 16.2 × log(LOC)) × 100 / 171)
    where HV is the Halstead Volume, CC the Cyclomatic Complexity, and LOC the logical source lines of code.
    The result is normalized to a value between 0 and 100, with higher values indicating more maintainable code.
    If the assembly PDB file is found, the CyclomaticComplexity and NbLinesOfCode are inferred from the source code. Otherwise ILCyclomaticComplexity and NbILInstructions are taken instead in a slightly adapted formula that leads to less accurate values.
    Recommendations:
    Code elements with a Maintainability Index above 85 are considered easy to maintain.
    Values between 50 and 85 suggest moderate maintainability.
    Values below 50 indicate hard-to-maintain elements, and refactoring should be considered (except for code generated automatically by a tool).
    Code automatically generated methods may exhibit artificially high or low values.

    NbILInstructions

    Gets a numeric nullable value counting the number of IL instructions for this code element.

    uint? NbILInstructions { get; }

    Property Value

    uint?

    null if this code element is defined in a third-party assembly.
    null if this code element is an interface, an enumeration or an abstract method.
    Otherwise returns the number of IL instructions for this code element.

    Remarks

    The number of IL instructions can vary depending if an application assembly is compiled in debug or in release mode.
    Indeed compiler's optimizations can modify the number of IL instructions.
    For example a compiler can add some nop IL instructions in debug mode, to handle Edit and Continue, or to allow attaching an IL instruction to a curly brace.

    NbLinesOfCode

    Gets a numeric nullable value counting the number of logical lines of code for this code element.

    uint? NbLinesOfCode { get; }

    Property Value

    uint?

    null if this code element is defined in a third-party assembly.
    null if the PDB file of this assembly or code element parent's assembly, hasen't been found.
    null if this code element is an interface, an enumeration, an abstract method or a default constructor.
    Otherwise returns the number of logical lines of code for this code element.

    Remarks

    This metric (known as LoC) can be computed only if PDB files are present.
    NDepend computes this metric directly from the information provided in PDB files.
    The LoC for a method is equal to the number of sequence points found for this method in the PDB file.
    A sequence point is used to mark a spot in the IL code that corresponds to a specific location in the original source.
    More info about sequence points can be found here
    Notice that sequence points which correspond to C# braces‘{‘ and ‘}’ are not taken account.
    Computing the number of lines of code from PDB’s sequence points allows to obtain a logical LoC of code instead of a physical LoC (i.e directly computed from source files).
    Two significant advantages of logical LoC over physical LoC are:

    • Coding style doesn’t interfere with logical LoC. For example the LoC won’t change because a method call is spawn on several lines because of a high number of arguments.
    • Logical LoC is independent from the programming language. Values obtained from assemblies written with different languages are comparable and can be summed.
    Notice that the LoC for a type is the sum of its methods’ LoC, the LoC for a namespace is the sum of its types’ LoC, the LoC for an assembly is the sum of its namespaces’ LoC and the LoC for a code base is the sum of its application assemblies LoC.
    Here are some observations:
    • Interfaces, abstract methods and enumerations have a NbLinesOfCode value equals to null. Only concrete code that is effectively executed is considered when computing LoC.
    • Namespaces, types, fields and methods declarations are not considered as line of code because they don’t have corresponding sequence points.
    • When the C# or VB.NET compiler faces an inline instance fields initialization, it generates a sequence point for each of the instance constructor (the same remark applies for inline static fields initialization and static constructor).
    • LoC computed from an anonymous method doesn’t interfere with the LoC of its outer declaring methods.
    • The overall ratio between NbILInstructions and LoC (in C# and VB.NET) is usually around 7.
    Recommendations:
    Methods where NbLinesOfCode is higher than 20 are hard to understand and maintain.
    Methods where NbLinesOfCode is higher than 40 are extremely complex and should be split in smaller methods (except if they are automatically generated by a tool).

    NbLinesOfCodeCovered

    Gets a numeric nullable value in the range [0,this.NbLinesOfCode] counting the number of lines of code of this code element, covered by tests.

    uint? NbLinesOfCodeCovered { get; }

    Property Value

    uint?
  • null if no code coverage data are imported through the NDepend project settings IProjectCoverage.
  • null if this code element is defined in a third-party assembly.
  • null if the PDB file of this assembly or code element parent's assembly, hasen't been found.
  • null if the code element is tagged with the attribute defined in IProjectCoverage.UncoverableAttribute.
  • null if the code element does not contain any PDB sequence point.
  • 0 if the code element NbLinesOfCode is 0 and the code element contains at least one PDB sequence point (opening/closing braces have sequence points but don't count as lines of code).
  • Otherwise returns the number of lines of code covered by tests for this code element.
  • Notice that if a code element parent (assembly/namespace/type) contains some child code elements tagged with IProjectCoverage.UncoverableAttribute the lines of code of these child code elements are not counted neither in NbLinesOfCodeCovered nor in NbLinesOfCodeNotCovered.
    See Also

    NbLinesOfCodeNotCovered

    Gets a numeric nullable value in the range [0,this.NbLinesOfCode] counting the number of lines of code of this code element, not covered by tests.

    uint? NbLinesOfCodeNotCovered { get; }

    Property Value

    uint?
  • null if no code coverage data are imported through the NDepend project settings IProjectCoverage.
  • null if this code element is defined in a third-party assembly.
  • null if the PDB file of this assembly or code element parent's assembly, hasen't been found.
  • null if the code element is tagged with the attribute defined in IProjectCoverage.UncoverableAttribute.
  • null if the code element does not contain any PDB sequence point.
  • 0 if the code element NbLinesOfCode is 0 and the code element contains at least one PDB sequence point (opening/closing braces have sequence points but don't count as lines of code).
  • Otherwise returns the number of lines of code not covered by tests for this code element.
  • Notice that if a code element parent (assembly/namespace/type) contains some child code elements tagged with IProjectCoverage.UncoverableAttribute the lines of code of these child code elements are not counted neither in NbLinesOfCodeCovered nor in NbLinesOfCodeNotCovered.
    See Also

    NbLinesOfComment

    Gets a numeric nullable value counting the number of lines of comments contained in the body of this code element.

    uint? NbLinesOfComment { get; }

    Property Value

    uint?

    null if this code element is defined in a third-party assembly.
    null if the PDB file of this assembly or code element parent's assembly, hasen't been found.
    null if the source code file path referenced from the PDB file cannot be found.
    null if the source code of this code element is written with a programming language different than C#.
    Otherwise returns the number of comments for this code element.

    Remarks

    This metric can be computed only if assemblies PDB files are found at analysis-time and if corresponding source files can be found.
    So far this metric is only computed for C# code and a VB.NET version will be released in the future.
    The number of lines of comment is computed as follow:

    • For a method, this metric value is the number of lines of comment that can be found in its body. In C# the body of a method begins with a '{' and ends with a '}'. If a method contains an anonymous method, lines of comment defined in the anonymous method are not counted for the outer method but are counted for the anonymous method.
    • For a type, this metric value is the sum of the number of lines of comment that can be found in each of its partial definition. In C#, each partial definition of a type begins with a '{ and ends with a '}'.
    • For a namespace, this metric value is the sum of the number of lines of comment that can be found in each of its partial definition. In C# each partial definition of a namespace begins with a '{ and ends with a '}'.
    • For an assembly, this metric value is the sum of the number of lines of comment that can be found in each of its source file.
    Notice that this metric is not an additive metric (i.e for example, the number of lines of comment of a namespace can be greater than the number of lines of comment over all its types).
    Recommendations:

    This metric is not helpful to assess the quality of source code from a commenting perspective. Prefer using the metric PercentageComment.

    PercentageComment

    Gets a numeric float nullable value in the range [0,100] assessing the percentage of comments for this code element.

    float? PercentageComment { get; }

    Property Value

    float?

    null if this code element is defined in a third-party assembly.
    null if the PDB file of this assembly or code element parent's assembly, hasen't been found.
    null if the source code file path referenced from the PDB file cannot be found.
    null if the source code of this code element is written with a programming language different than C#.
    Otherwise returns the comments percentage for this code element.

    Remarks

    This metric value is computed with the following formula: PercentageComment = 100*NbLinesOfComment / ( NbLinesOfComment + NbLinesOfCode).

    Recommendations:
    Code where the percentage of comment is lower than 20% might need to be more commented. However overly commented code (more than 40%) is not necessarily a blessing as it can be considered as an insult to the intelligence of the reader.
    Guidelines about code commenting can be found here.

    PercentageCoverage

    Gets a numeric float nullable value in the range [0f,100f] assessing the coverage percentage for this code element.

    float? PercentageCoverage { get; }

    Property Value

    float?
  • null if no code coverage data are imported through the NDepend project settings IProjectCoverage.
  • null if this code element is defined in a third-party assembly.
  • null if the PDB file of this assembly or code element parent's assembly, hasen't been found.
  • null if the code element is tagged with the attribute defined in IProjectCoverage.UncoverableAttribute.
  • null if the code element does not contain any PDB sequence point.
  • 0 if the code element NbLinesOfCode is 0 and the code element contains at least one PDB sequence point (opening/closing braces have sequence points but don't count as lines of code).
  • Otherwise returns the code coverage by tests percentage for this code element computed as NbLinesOfCodeCovered / (NbLinesOfCodeCovered + NbLinesOfCodeNotCovered).
  • Notice that if a code element parent (assembly/namespace/type) contains some child code elements tagged with IProjectCoverage.UncoverableAttribute the lines of code of these child code elements are not counted neither in NbLinesOfCodeCovered nor in NbLinesOfCodeNotCovered.
    As a consequence (NbLinesOfCodeCovered + NbLinesOfCodeNotCovered) can be lower than NbLinesOfCode.
    As a consequence a code element can have 100% code coverage, even if NbLinesOfCodeCovered is lower than NbLinesOfCode, as long as NbLinesOfCodeNotCovered value is 0.

    Remarks

    Recommendations:
    The closer to 100%, the better!
    See Also