Ambiguous use of 'filter' when converting project to Swift 4
To solve this, declare the type of the variable before you return it.
let x: [Character] = input.filter{/**/}
return x
This disambiguates the return type of the filter{} method.
Ambiguous use of 'filter' after migration to Swift 4.2
You have added your own filter
method to Dictionary
, this is not necessary, as Swift already has such a method: filter
.
This method seems to be added in Swift 4.2, which explains why you didn't get the error before. Since Swift has this method provided for you now, you can safely delete the filter
that you wrote.
Swift 4 - Ambigous reference to member '' (iOS 11)
The value
is a generic method and when comparing with a literal (that is, something without a defined type), the compiler has a problem to figure out what type to infer there. One workaround is to add as Int
to one side of the expression:
(slightly rewritten for readability)
let alerts = realm.objects(Alerts).filter(NSPredicate(format: "department != nil")).sorted(byKeyPath: "departmentNumber")
let isRedLevel: (DangerLevel) -> Bool = { dangerLevel in
($0.level.value as Int) == 4
}
let hasRedLevels: (Alert) -> Bool = { alert in
alert.dangerLevels.contains(where: isRedLevel)
}
redCount = alerts!.filter(hasRedLevels).count
What would also work is to define a constant:
let redAlertType: Int = 4
and use it instead of the literal 4
.
Wanted to see if anyone has any insight to why an ambigious use of subscript error is created in one project vs. another in swift
As is explained in the answer you linked to, Foundation containers (NSArray
, NSDictionary
etc) are untyped. So, currentSelectionCells[row]
returns AnyObject
. Swift won't let you subscript an AnyObject
since it may not be a container. It could literally be anything.
If you look closely at the code in the AppCoda article where you have
for row in 0...((currentSectionCells ).count - 1) {
they have
for row in 0...((currentSectionCells as! [[String: AnyObject]]).count - 1) {
They have bridged currentSelectCells
to a Swift array containing a Swift dictionary of String:AnyObject
so when they later say currentSelectionCells[row]
they get back a dictionary [String:AnyObject]
. This is subscriptable and Swift is happy.
So, there is an easy way to convert a plist to a Swift array. It is generally best to convert Foundation containers to Swift containers at the earliest opportunity since then you get the advantages of member typing. It would have been better if they had implemented loadCellDescriptors
as something like:
var cellDescriptors: [[String:AnyObject]]!
func loadCellDescriptors() {
if let path = NSBundle.mainBundle().pathForResource("CellDescriptor", ofType: "plist") {
let plist = NSMutableArray(contentsOfFile: path)
cellDescriptors = plist as! [[String:AnyObject]]
getIndicesOfVisibleRows()
tblExpandable.reloadData()
}
}
Explain this code: uses a string as filter function
It's using:
// MARK: Filtering
/**
Returns a `Results` containing all objects matching the given predicate in the collection.
- parameter predicateFormat: A predicate format string, optionally followed by a variable number of arguments.
*/
func filter(_ predicateFormat: String, _ args: Any...) -> Results<Element>
Source: RealmCollectiton
Under the hood, it's using NSPredicate(format:)
, it "hides" it by simplifying and avoid writing each time NSPredicate(format: ...)
, and should use KeyPath too. More explanation on what you can do with that here at Predicate Format String Syntax.
not
func filter(_ isIncluded: (Self.Element) throws -> Bool) rethrows -> [Self.Element]
on Sequence
Here a sample code to illustrate/mimic:
class TestClass: NSObject {
@objc var title: String
init(title: String) {
self.title = title
super.init()
}
override var description: String {
"TestClass - title: \(title)"
}
}
let objects: [TestClass] = [TestClass(title: "Title1"), TestClass(title: "Title2")]
// In a "Swifty way
let searchedText = "Title1"
let filtered1 = objects.filter {
$0.title == searchedText
}
print("filtered1: \(filtered1)")
// With a NSPredicate, which is more Objective-C (filtering on NSArray for instance)
// But also there is a translation with Core-Data, and then fetching optimization
let filtered2 = objects.filter {
NSPredicate(format: "title == 'Title1'").evaluate(with: $0)
}
print("filtered2: \(filtered2)")
// Same, but with avoiding hard coding strings
let filtered3 = objects.filter {
NSPredicate(format: "%K == %@", #keyPath(TestClass.title), searchedText).evaluate(with: $0)
}
print("filtered3: \(filtered3)")
extension Sequence {
func filter(_ predicateFormat: String, _ args: Any...) -> [Element] {
let predicate = NSPredicate(format: predicateFormat, argumentArray: args)
return self.filter({ predicate.evaluate(with: $0) })
}
}
// With an extension similar to what does Realm
let filtered4 = objects.filter("title == 'Title1'")
print("filtered4: \(filtered4)")
// With an extension similar to what does Realm, and less hard coded string (cf filtered3 construction)
let filtered5 = objects.filter("%K == %@", #keyPath(TestClass.title), searchedText)
print("filtered5: \(filtered5)")
With output:
$>filtered1: [TestClass - title: Title1]
$>filtered2: [TestClass - title: Title1]
$>filtered3: [TestClass - title: Title1]
$>filtered4: [TestClass - title: Title1]
$>filtered5: [TestClass - title: Title1]
Type of expression is ambiguous without more context. SocketEngine Class
You should not update the library's functions to Swift 4 manually.
Download the library again, it has now been updated to Swift 4.
Dynamic Filter in Sqlite.swift to check if a column is not null
To check for inequality between an expression and an optional value with SQLite.swift, you need !==
, not !=
Here is the relevant code:
https://github.com/stephencelis/SQLite.swift/blob/master/Sources/SQLite/Typed/Operators.swift#L450
You can also see this in the tests:
https://github.com/stephencelis/SQLite.swift/blob/master/Tests/SQLiteTests/Typed/OperatorsTests.swift#L214
When you don't find something in the docs, the tests in this project are a good place to look for answers
Ambiguous use of 'init'
I found solution for my issue , I use same method name with deferent parameter in Objective-C Class
- (instancetype)initWithCoordinate:(CLLocationCoordinate2D)coordinate
Dragable:(BOOL)isDragable
updateCoordinate:(updateCoordinate)updateCoordinate;
and
- (instancetype)initWithCoordinate:(CLLocationCoordinate2D)coordinate
Dragable:(BOOL)isDragable;
just used
NS_SWIFT_NAME
to change names and it's work fine
NS_SWIFT_NAME(init(withUpdateCoordinateAndCoordinate:isDragable:withUpdateCoordinate:));
and
NS_SWIFT_NAME(init(withCoordinate:isDragable:));
Related Topics
Bridgetoobjectivec Not Available on Swift Beta 5
Cannot Convert Value of Type 'X' to Expected Argument Type 'X'
Realm: Predicate Returning Lazyfiltercollection - How to Convert to Results<T>
Avspeechrecognizer: Required Condition Is False: _Recordingtap == Nil Error in Swift3
Struct Memberwise Initialization - Omitting Values for Properties That Have Defaults
How to Access to a Static Cell
Swiftui: UIimage (Qrcode) Does Not Load After Calling Function
In Swift 5, What Is a Way to Compare Pointers to Two Closures
How to Split a String at The Last Occurence of a Sequence
How to Get Wkwebview to Work in Swift and for an Macos App
Nstoolbarflexiblespaceitem Is Constraint to Nssplitviewitem in Swift
How to Call Completionhandler for Performfetchwithcompletionhandler in Swift
Ambiguous Reference to Member 'Buildblock()'
Convert/Wrap Swift Struct as Nsvalue for Caanimation Purposes
Why Swift Call Too Shallow Here
How to a Convert a Dictionary Slice to a Dictionary in Swift