awaitable 하지 않은 델리게이트이거나 await 하지 않고 호출하는 델리게이트의 경우
델리게이트가 null 인지 여부를 ?
키워드를 통해 사용할 수 있지요.
Func<string> func = null;
func?.Invoke();
뭐 요딴식으루 말이죠.
근데 awaitable 한 델리게이트를 await 과 함께 사용하면
?
키워드로 null 체크 식을 사용할 수가 없어욜…
Func<Task> func = null;
await func?.Invoke();
이건 사실 문법적으로도 말이 안 되긴 해요.
(func 가 null 이면 await 키워드가 에러죠.)
그래서 그냥 null 체크 조건문을 만들어 쓰긴 합니다.
Func<Task> func = null;
if (func is not null)
{
await func();
}
아…
근데 저 ?
키워드를 사용해서 식으루 표현하는 게 참 아숩단 말이죵… ;ㅂ;
혹시 방법이 있을까요?ㅅ?
아님 혹시 다른 분들은 어떻게 사용하시나욜?ㅂ?
3개의 좋아요
세가지 정도 방법이 있지 않을까 합니다. 저 같은 경우 첫번째 방법을 선호합니다.
첫번째 방법 : null은 없다
Func<Task> funcAsync = () => Task.CompletedTask;
await funcAsync();
funcAsync
는 null
을 허용하지 않습니다. 그러므로 편하게 await
을 사용할 수 있습니다.
단점은 프로젝트 설정에 <Nullable>enable</Nullable>
을 줄 수 있는 환경만 해당되겠습니다.
두번째 방법 : null인 경우 Task.CompletedTask
호출
Func<Task>? funcAsync2 = null;
await (funcAsync2?.Invoke() ?? Task.CompletedTask);
??
를 이용해 null
인 경우 Task.CompleteTask
를 반환하도록 합니다. 어쨌든 한줄로 쓸 수 있어서 조금 보완된 느낌입니다만 깔끔해 보이지는 않습니다.
세번째 방법 : 확장 메소드로 좀 더 깔끔하게
Func<Task>? funcAsync3 = null;
await funcAsync3.InvokeAsync();
public static class FuncTaskExtension
{
public static Task InvokeAsync(this Func<Task>? @this) => @this?.Invoke() ?? Task.CompletedTask;
}
이건 사실 두번째 방법을 좀 더 깔끔하게 사용하는 방법입니다.
4개의 좋아요
func?.Invoke().ContinueWith(...);
이 방법도 있습니다.
3개의 좋아요
음… 이렇게 하면 async / await 를 사용 못 할 거 같은디요… ㅇㅁㅇ?
1개의 좋아요
아… async/await 키워드 관점에서는 사용할 수 없겠네요…
다만 동작으로 바라본다면 꽤 요긴하게 쓰이긴 합니다
1개의 좋아요