Skip to content

[stdlib] Dictionary.values: Replace setter with _modify #19497

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Sep 24, 2018

Conversation

lorentey
Copy link
Member

@lorentey lorentey commented Sep 24, 2018

This should enable in-place modification of the Values view, which should greatly improve the performance of code like this:

dictionary.values[index] = newValue

https://bugs.swift.org/browse/SR-5258 / rdar://problem/44725826

This should enable in-place modification of the Values view, which should greatly improve the performance of code like this:

dictionary.values[index] = newValue
@lorentey
Copy link
Member Author

@swift-ci please smoke test

@lorentey
Copy link
Member Author

@swift-ci please smoke benchmark

@lorentey
Copy link
Member Author

I think we actually have some benchmarks for this.

@swift-ci
Copy link
Contributor

Build comment file:

Build failed before running benchmark.


@lorentey
Copy link
Member Author

lorentey commented Sep 24, 2018

Oops, Dictionary.Values.init(_variant:) has not yet landed with #19496

@lorentey
Copy link
Member Author

@swift-ci please smoke benchmark

@lorentey
Copy link
Member Author

@swift-ci please smoke test

@airspeedswift
Copy link
Member

Interesting. This is similar to yielding a Slice, but sidesteps almost all of the issues slice has because Values doesn't have a public init.

Should there be a (debug?) postcondition that the user didn't replace one instance of Values with another from a different Dictionary?

@lorentey
Copy link
Member Author

I guess it is slightly weird that assigning to values might affect keys, but would it cause any issues in practice?

dict.values = someOtherDict.values   // same as dict = someOtherDict

It seems technically difficult to verify the identity doesn't change. We could remember the raw bit pattern for it, but it wouldn't be foolproof -- the yieldee could end up releasing it and allocating a new one at the same address.

@airspeedswift
Copy link
Member

Oh, right, replacing the values replaces the entire dictionary, so it is safe, if confusing. A debug trap might be useful for a case where someone mistakenly thinks it does something different though.

@swift-ci
Copy link
Contributor

Build comment file:

Performance: -O

TEST OLD NEW DELTA RATIO
Improvement
DictionarySwapAt 5076 908 -82.1% 5.59x
DictionarySwapAtOfObjects 49768 9443 -81.0% 5.27x

Performance: -Osize

TEST OLD NEW DELTA RATIO
Improvement
DictionarySwapAtOfObjects 49987 10099 -79.8% 4.95x
DictionarySwapAt 5253 1328 -74.7% 3.96x

Performance: -Onone

TEST OLD NEW DELTA RATIO
Improvement
DictionarySwapAtOfObjects 113144 35401 -68.7% 3.20x
DictionarySwapAt 34148 17177 -49.7% 1.99x
How to read the data The tables contain differences in performance which are larger than 8% and differences in code size which are larger than 1%.

If you see any unexpected regressions, you should consider fixing the regressions before you merge the PR.

Noise: Sometimes the performance results (not code size!) contain false alarms. Unexpected regressions which are marked with '(?)' are probably noise. If you see regressions which you cannot explain you can try to run the benchmarks again. If regressions still show up, please consult with the performance team (@eeckstein).

Hardware Overview
  Model Name: Mac Pro
  Model Identifier: MacPro6,1
  Processor Name: 12-Core Intel Xeon E5
  Processor Speed: 2.7 GHz
  Number of Processors: 1
  Total Number of Cores: 12
  L2 Cache (per Core): 256 KB
  L3 Cache: 30 MB
  Memory: 64 GB

@lorentey
Copy link
Member Author

The setter didn't include a trap, so adding it in _modify would technically be a source-breaking change. We should probably make a separate issue for it.

@airspeedswift
Copy link
Member

Yeah it's not a new issue for this change.

@lorentey lorentey merged commit cc3db35 into swiftlang:master Sep 24, 2018
@lorentey lorentey deleted the dictionary-values-accessor branch September 24, 2018 20:46
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants