Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Conversation

stevejgordon
Copy link
Contributor

Closes #104015

Adds a new constructor, as proposed, to optimize the scenario where a TagsList is provided to construct a new Measurement. This avoids boxing allocations and reduces execution time.

| Method     | Size | Mean      | Error     | StdDev    | Ratio    | RatioSD | Gen0   | Allocated | Alloc Ratio |
|----------- |----- |----------:|----------:|----------:|---------:|--------:|-------:|----------:|------------:|
| TagList    | 1    | 20.746 ns | 0.3769 ns | 0.4033 ns | baseline |         | 0.0159 |     200 B |             |
| TagListNew | 1    |  7.627 ns | 0.1620 ns | 0.1516 ns |     -63% |    3.1% | 0.0032 |      40 B |        -80% |
|            |      |           |           |           |          |         |        |           |             |
| TagList    | 8    | 44.965 ns | 0.9227 ns | 1.1331 ns | baseline |         | 0.0249 |     312 B |             |
| TagListNew | 8    | 29.285 ns | 0.5105 ns | 0.4526 ns |     -35% |    2.7% | 0.0121 |     152 B |        -51% |
|            |      |           |           |           |          |         |        |           |             |
| TagList    | 20   | 31.073 ns | 0.6176 ns | 0.6066 ns | baseline |         | 0.0402 |     504 B |             |
| TagListNew | 20   | 18.474 ns | 0.3874 ns | 0.4757 ns |     -40% |    3.2% | 0.0274 |     344 B |        -32% |

I also took the chance to fix and clarify the XML doc comments.

cc @tarekgh

@ghost
Copy link

ghost commented Jul 17, 2024

Note regarding the new-api-needs-documentation label:

This serves as a reminder for when your PR is modifying a ref *.cs file and adding/modifying public APIs, please make sure the API implementation in the src *.cs file is documented with triple slash comments, so the PR reviewers can sign off that change.

@ghost
Copy link

ghost commented Jul 17, 2024

Note regarding the new-api-needs-documentation label:

This serves as a reminder for when your PR is modifying a ref *.cs file and adding/modifying public APIs, please make sure the API implementation in the src *.cs file is documented with triple slash comments, so the PR reviewers can sign off that change.

@dotnet-policy-service dotnet-policy-service bot added the community-contribution Indicates that the PR has been added by a community member label Jul 17, 2024
Copy link
Contributor

Tagging subscribers to this area: @tarekgh, @tommcdon, @pjanotti
See info in area-owners.md if you want to be subscribed.

@stevejgordon stevejgordon force-pushed the measurement-taglist-ctor branch from 6f71707 to d137fd0 Compare July 17, 2024 05:49
@stephentoub
Copy link
Member

This avoids boxing allocations

With the params span ctor, why were there boxing allocations?

@tarekgh
Copy link
Member

tarekgh commented Jul 17, 2024

With the params span ctor, why were there boxing allocations?

This is because the constructor accepting the IEnumerable<> will be used.

        TagList list = new TagList { { "Key", "Value" } };
        Measurement<int> measurement = new Measurement<int>(10, list);
        IL_0000: nop
        IL_0001: ldloca.s 2
        IL_0003: initobj [System.Diagnostics.DiagnosticSource]System.Diagnostics.TagList
        IL_0009: ldloca.s 2
        IL_000b: ldstr "Key"
        IL_0010: ldstr "Value"
        IL_0015: call instance void [System.Diagnostics.DiagnosticSource]System.Diagnostics.TagList::Add(string, object)
        IL_001a: nop
        IL_001b: ldloc.2
        IL_001c: stloc.0
        IL_001d: ldloca.s 1
        IL_001f: ldc.i4.s 10
        IL_0021: ldloc.0
        IL_0022: box [System.Diagnostics.DiagnosticSource]System.Diagnostics.TagList
        IL_0027: call instance void valuetype [System.Diagnostics.DiagnosticSource]System.Diagnostics.Metrics.Measurement`1<int32>::.ctor(!0, class [System.Runtime]System.Collections.Generic.IEnumerable`1<valuetype [System.Runtime]System.Collections.Generic.KeyValuePair`2<string, object>>)
        IL_002c: ret

@stephentoub
Copy link
Member

This is because the constructor accepting the IEnumerable<> will be used.

Ok, I thought Steve was talking about doing e.g.

Measurement<int> measurement = new Measurement<int>(
    10,
    new KeyValuePair<string, object?>("a", "b"),
    new KeyValuePair<string, object?>("c", "d"),
    new KeyValuePair<string, object?>("e", "f"),
    new KeyValuePair<string, object?>("g", "h"));

which should no longer allocate or box at the call site. That should now bind to the params ReadOnlySpan<...> overload.

@tarekgh tarekgh merged commit 6c32206 into dotnet:main Jul 17, 2024
@stevejgordon stevejgordon deleted the measurement-taglist-ctor branch July 17, 2024 21:46
/// </summary>
/// <param name="value">The value of the measurement.</param>
/// <param name="tags">A <see cref="TagList"/> containing the <see cref="KeyValuePair{TKey, TValue}"/> tags associated with the measurement.</param>
public Measurement(T value, in TagList tags)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we have tests for this? I don't see any in this PR.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

var measurement = new Measurement<int>(i, tags);

@github-actions github-actions bot locked and limited conversation to collaborators Sep 8, 2024
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

[API Proposal]: Add TagList constructor to Measurement
4 participants