Xcode 9.2, Swift 4
class AsyncOperation {
typealias NumberOfPendingActions = Int
typealias DispatchQueueOfReturningValue = DispatchQueue
typealias CompleteClosure = ()->()
private let dispatchQueue: DispatchQueue
private var semaphore: DispatchSemaphore
private var numberOfPendingActionsQueue: DispatchQueue
public private(set) var numberOfPendingActions = 0
var whenCompleteAll: (()->())?
init(numberOfSimultaneousActions: Int, dispatchQueueLabel: String) {
dispatchQueue = DispatchQueue(label: dispatchQueueLabel)
semaphore = DispatchSemaphore(value: numberOfSimultaneousActions)
numberOfPendingActionsQueue = DispatchQueue(label: dispatchQueueLabel + "_numberOfPendingActionsQueue")
}
func run(closure: @escaping (@escaping CompleteClosure)->()) {
self.numberOfPendingActionsQueue.sync {
self.numberOfPendingActions += 1
}
dispatchQueue.async {
self.semaphore.wait()
closure {
self.numberOfPendingActionsQueue.sync {
self.numberOfPendingActions -= 1
if self.numberOfPendingActions == 0 {
self.whenCompleteAll?()
}
}
self.semaphore.signal()
}
}
}
}
let asyncOperation = AsyncOperation(numberOfSimultaneousActions: 1, dispatchQueueLabel: "AnyString")
asyncOperation.whenCompleteAll = {
print("All Done")
}
for i in 0...5 {
print("\(i)")
asyncOperation.run{ completeClosure in
// add any (sync/async) code
//..
// Make signal that this closure finished
completeClosure()
}
}
import UIKit
class ViewController: UIViewController {
let asyncOperation = AsyncOperation(numberOfSimultaneousActions: 3, dispatchQueueLabel: "AnyString")
let button = UIButton(frame: CGRect(x: 50, y: 80, width: 100, height: 40))
let label = UILabel(frame: CGRect(x: 180, y: 50, width: 150, height: 100))
var counter = 1
var labelCounter = 0
override func viewDidLoad() {
super.viewDidLoad()
button.setTitle("Button", for: .normal)
button.setTitleColor(.blue, for: .normal)
button.addTarget(self, action: #selector(buttonTapped), for: .touchUpInside)
label.text = "\(labelCounter)"
label.numberOfLines = 2
label.textAlignment = .natural
view.addSubview(button)
view.addSubview(label)
}
@objc func buttonTapped() {
//sample1()
sample2()
}
func sample1() {
print("Sample 1")
labelCounter += 1
label.text = "button tapped \(labelCounter) times"
print("Button tapped at: \(Date())")
asyncOperation.whenCompleteAll = {
print("All Done")
}
asyncOperation.run{ completeClosure in
let counter = self.counter
print(" - Loading action \(counter) strat at \(Date())")
self.counter += 1
DispatchQueue.global(qos: .background).async {
sleep(1)
print(" - Loading action \(counter) end at \(Date())")
completeClosure()
}
}
}
func sample2() {
print("Sample 2")
label.text = ""
asyncOperation.whenCompleteAll = {
print("All Done")
}
for i in 0...5 {
asyncOperation.run{ completeClosure in
let counter = self.counter
print(" - Loading action \(counter) strat at \(Date())")
self.counter += 1
DispatchQueue.global(qos: .background).async {
sleep(UInt32(i+i))
print(" - Loading action \(counter) end at \(Date())")
completeClosure()
}
}
}
}
}
Образец 1
Образец 2
Используйте Double.valueOf()
и приведите результат к long
:
Double.valueOf("9.18E+09").longValue()
BigDecimal bd = new BigDecimal("9.18E+09");
long val = bd.longValue();
Но это добавляет накладные расходы, которые не нужны для небольших чисел. Для чисел, которые можно представить в long
, используйте решение Йоахима Зауэра.