Asynchronous & Synchronous
聞き慣れない単語だが
Asynchronous & Synchronous聞き慣れない単語ですね。非同期処理のPromise
とasync/await
と同期処理なら知っている。海外の動画でiOSの学習をしていたときに出てきました。
実はこれ知ってる表現でした。
MDNに解説があったので読んでいただけるとご理解いただけると思います。
Asynchronous (非同期)
公式より引用
非同期 (asynchronous) という用語は、 2 つ以上のオブジェクトやイベントが同時に存在しない、または起こらない、すなわち同期していないことを表します。複数の関連のあることが、前回起こったことの完了に依存することなく起こるとき、それらは非同期です。
他の処理を待たずに実行することできる。趣味で作った本に書いていたTypeScriptのソースコードを例に出すとこんな感じですかね。
// Promiseを使ってhttps://jsonplaceholderからデータを非同期に取得する
function fetchUser(): Promise<void> {
return new Promise((resolve, reject) => {
fetch("https://jsonplaceholder.typicode.com/users")
.then((res) => res.json())
.then((users) => {
console.log(users);
resolve(users);
});
});
}
fetchUser()
.then((users) => {
// データを取得した後の処理
console.log(users);
})
.catch((err) => {
// エラーが発生した場合の処理
console.log(err);
});
Promiseを短くかけるシンタックスシュガーのasync/awaitもある。よく使われるのはこっち。
// async/awaitを使ってhttps://jsonplaceholderからデータを非同期に取得する
async function AsyncUser(): Promise<void> {
try {
// 成功した場合の処理
const res = await fetch("https://jsonplaceholder.typicode.com/users");
const users = await res.json();
console.log(users);
} catch (err) {
// エラーが発生した場合の処理
console.log(err);
}
}
AsyncUser();
iOSの場合だと別のアカウントで書いていた記事があったのですが、こちらですね。
import SwiftUI
// MARK: - Models
struct User: Codable, Identifiable {
let id = UUID()
let login: String
let url: String
let avatar_url: String
let html_url: String
}
struct APIResponse: Codable {
let items: [User]
}
// MARK: - ViewModel
enum FetchState {
case idle
case loading
case loaded([User])
case error(Error)
}
class UserViewModel: ObservableObject {
@Published var fetchState: FetchState = .idle
func getUsers() {
fetchState = .loading
Task {
let result = await fetchUsers()
DispatchQueue.main.async {
switch result {
case .success(let users):
self.fetchState = .loaded(users)
case .failure(let error):
self.fetchState = .error(error)
}
}
}
}
private func fetchUsers() async -> Result<[User], Error> {
guard let apiURL = URL(string: "https://api.github.com/search/users?q=greg") else {
return .failure(NSError(domain: "", code: 0, userInfo: [NSLocalizedDescriptionKey: "Invalid URL"]))
}
do {
let (data, _) = try await URLSession.shared.data(from: apiURL)
let apiResponse = try JSONDecoder().decode(APIResponse.self, from: data)
return .success(apiResponse.items)
} catch {
return .failure(error)
}
}
}
// MARK: - Views
struct LoadingView: View {
var body: some View {
VStack {
ProgressView().padding()
Text("Fetching Users...")
}
}
}
struct UserListView: View {
let users: [User]
var body: some View {
List(users) { user in
Link(destination: URL(string: user.html_url)!) {
HStack {
AsyncImage(url: URL(string: user.avatar_url)) { phase in
switch phase {
case .success(let image):
image.resizable().frame(width: 50, height: 50)
default:
Image(systemName: "nosign")
}
}
VStack(alignment: .leading) {
Text(user.login)
Text(user.url)
.font(.system(size: 11))
.foregroundColor(Color.gray)
}
}
}
}
}
}
struct ContentView: View {
@StateObject private var viewModel = UserViewModel()
var body: some View {
NavigationStack {
Group {
switch viewModel.fetchState {
case .idle:
Text("Tap to load users")
case .loading:
LoadingView()
case .loaded(let users):
UserListView(users: users)
case .error(let error):
Text("Error: \(error.localizedDescription)")
}
}
.navigationTitle("GitHub Users")
}
.onAppear {
viewModel.getUsers()
}
}
}
#Preview {
ContentView()
}
少し前に書いたGitHubサーチするコードですがまだ動きます。参考までに試してみてください。
Synchronous (同期通信方式)
公式より引用
同期 (Synchronous) とは、各当事者がメッセージを瞬時に(または可能な限り直ちに)受信(また必要な場合には処理および返信)するリアルタイムのコミュニケーションのことを指します。
人間での例としては電話が挙げられます。電話の通話中は、あなたは通話相手に直ちに返事をしやすいです。
プログラミングのコマンドの多くも同期的です。例えば、計算式を入力すると、環境は即座にその結果を返します(そうならないようにプログラムをしない限り)。
よくあるコードが同期処理と呼ばれているものですね。他の処理が実行されるのを待ってい実行されるという表現を聞きますね。
SwiftのforEachをコードでロジックを解説すると。。。
「forEach は同期的に動作します。各要素に対するクロージャは、前の処理が終わってから次の処理が順番に実行されるため、常に順番通りに出力がされます。」
var arr: [Int] = [1, 2, 3, 4, 5]
arr.forEach({
if $0 == 5 {
print("要素数は同じ5です")
} else {
print("要素数は \($0)")
}
})
まとめ
海外の記事や動画を見たときに、Asynchronousというテキストが出てきたら非同期書、Synchronousというテキストが出てきたら同期処理と理解できるようになりました。
普段日本語で見てるもので英語だとこんな表現使うんですね。普段から専門用を英語で使うようにすると少しずつ外国の人のテキストの内容が理解できるようになりそう。
Discussion