Reputation: 191
I was thinking the following syntax:
extension Dictionary where Key:String,Value:String{
func addIfNew(key:String,value:String){
print("new item added: \(key) with value: \(value)")
}
}
For example: the function would log any new added data
Upvotes: 8
Views: 11470
Reputation: 17544
This should be enough ...
protocol P {}
extension String: P {}
extension Dictionary where Key:P, Value:P {
func addIfNew(key:String, value:String){
print("new item added: \(key) with value: \(value)")
}
}
let d:[String:String] = [:]
don't make other types conforming to P and you are fine
in Swift3
extension Dictionary where Key == String, Value == String {
func addIfNew(key:String, value:String){
print("new item added: \(key) with value: \(value)")
}
}
let d:[String:String] = [:]
d.addIfNew(key: "a", value: "A")
Upvotes: 15
Reputation: 8391
Not possible the way you want to do it. You can only constrain extensions
of Dictionary
to protocols
Key
and/or Value
conform too. Else you will just get more errors.
But you can do this :
extension String : CustomStringConvertible {
public var description : String { return self }
}
extension Dictionary where Key : CustomStringConvertible, Value : CustomStringConvertible {
func addIfNew(key:Key,value:Value){
print("new item added: \(key.description) with value: \(value.description)")
}
}
var dict : [String:String] = [:]
dict["blah"] = "foo"
dict.addIfNew("blah", value: "foo2")
Important is to ask yourself what you want.
Strings
Equatable
is good enoughIf Equatable
is good enough you can do this :
extension Dictionary where Value : Equatable {
mutating func addIfNew(key:Key,value:Value){
if self.values.contains(value) {
print("\(value) exists")
} else {
print("new item added: \(key) with value: \(value)")
self[key] = value
}
}
}
var dict : [String:String] = [:]
dict["blah"] = "foo"
dict.addIfNew("blah1", value: "foo2")
dict.addIfNew("blah2", value: "foo2")
Although this function will work on any Dictionary
whose Value
is Equatable
, you can choose to only use it on those that have String
as Value
If you really need it to only work on String
you need to create a custom protocol
and only have String
conform to it. The protocol
will need to have a computed property that returns self
because else you will not be able to print
it, since it isn't considered a String
inside the extension
.
protocol StringType : Hashable {
var value : String { get }
}
extension String : StringType {
var value : String { return self }
}
extension Dictionary where Key : StringType, Value : StringType {
mutating func addIfNew(key:Key,value:Value){
if self.values.contains(value) {
print("\(value.value) exists")
} else {
print("new item added: \(key.value) with value: \(value.value)")
self[key] = value
}
}
}
var dict : [String:String] = [:]
dict["blah"] = "foo"
dict.addIfNew("blah1", value: "foo2")
dict.addIfNew("blah2", value: "foo2")
Side note:
Since Dictionary
is a struct
functions need to be mutating
in order to alter self
.
Upvotes: 7