Change:
func ParseToRequirements(selector string, opts ...field.PathOption) ([]Requirement, error) { return parse(selector, field.ToPath(opts...)) } <ins> // ValidatedSetSelector wraps a Set, allowing it to implement the Selector interface. Unlike // Set.AsSelectorPreValidated (which copies the input Set), this type simply wraps the underlying // Set. As a result, it is substantially more efficient. A nil and empty Sets are considered // equivalent to Everything(). // // Callers MUST ensure the underlying Set is not mutated, and that it is already validated. If these // constraints are not met, Set.AsValidatedSelector should be preferred // // None of the Selector methods mutate the underlying Set, but Add() and Requirements() convert to // the less optimized version. type ValidatedSetSelector Set func (s ValidatedSetSelector) Matches(labels Labels) bool { for k, v := range s { if !labels.Has(k) || v != labels.Get(k) { return false } } return true } func (s ValidatedSetSelector) Empty() bool { return len(s) == 0 } func (s ValidatedSetSelector) String() string { keys := make([]string, 0, len(s)) for k := range s { keys = append(keys, k) } // Ensure deterministic output sort.Strings(keys) b := strings.Builder{} for i, key := range keys { v := s[key] b.Grow(len(key) + 2 + len(v)) if i != 0 { b.WriteString(",") } b.WriteString(key) b.WriteString("=") b.WriteString(v) } return b.String() } func (s ValidatedSetSelector) Add(r ...Requirement) Selector { return s.toFullSelector().Add(r...) } func (s ValidatedSetSelector) Requirements() (requirements Requirements, selectable bool) { return s.toFullSelector().Requirements() } func (s ValidatedSetSelector) DeepCopySelector() Selector { res := make(ValidatedSetSelector, len(s)) for k, v := range s { res[k] = v } return res } func (s ValidatedSetSelector) RequiresExactMatch(label string) (value string, found bool) { v, f := s[label] return v, f } func (s ValidatedSetSelector) toFullSelector() Selector { return SelectorFromValidatedSet(Set(s)) } var _ Selector = ValidatedSetSelector{} </ins>

Discussion:
A common pattern in Kubernetes (both internally and in third party usage) is something like: (this is from the ). This is commonly called at a fairly high rate; in our case we would actually end up seeing this account for significant portions of CPU/memory to compute the and run on it. In our controller, as an optimization, we replaced usage of and just used our own simpler label matching code, leading to a 70% speed up in our function (which does more than just match) and 96% allocation size improvement; see I believe similar could be done in Kubernetes directly by having a specialized Selector implementation for simple labels. This would transparently given substantial performance benefits to anyone using the library
/sig api-machinery
is the change here a new kind of selector matching or a tweak to something existing? It's hard to tell if this is proposing a new design to partition types of selectors that needs a kep versus a perf tweak to existing code that is straight-forward.
The proposal is an internal performance improvement to make a specialized implementation of the selector matching internally. So two concrete implementations for 1 shared interface. is a PoC of this. I think it can be extended (by me, or others if someone wants to) to complete it
We discussed this one during our bug triage. There seemed to be the feeling that this is large enough to need a KEP? Would you be up for that? Additionally you could bring it up in our SIG meeting to socialize / discuss it more if you wanted.
The patch shared in helps to explain, it's a lot smaller than the description made it sound. This is a special case for equality-only selectors. Probably still worth bringing up at a sig-meeting, but if if the patch is a good representation, it is more bounded than expected from the issue description.
/triage accepted