在C#中,是否可以重构Post和Put方法以消除代码重复?

我有以下两种方法:

        private string Post(string url,bytearraycontent content,AuthenticationToken token = null) {
            servicepointManager.SecurityProtocol = SecurityProtocolType.Tls12;

            using HttpClient client = new HttpClient();
            if (token != null) {
                client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer",token.access_token);
            }

            return client.PostAsync(url,content)
                .Result.Content.ReadAsStringAsync()
                .Result;
        }

        private string Put(string url,AuthenticationToken token) {
            servicepointManager.SecurityProtocol = SecurityProtocolType.Tls12;

            using HttpClient client = new HttpClient();
            if (token != null) {
                client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer",token.access_token);
            }

            return client.PutAsync(url,content)
                .Result.Content.ReadAsStringAsync()
                .Result;
        }

如您所见,唯一的区别是一个方法调用了PostAsync,而另一种方法调用了PutAsync

是否可以编写单个函数,如:

        private string Send(string url,AuthenticationToken token,String functionName) {
            servicepointManager.SecurityProtocol = SecurityProtocolType.Tls12;

            using HttpClient client = new HttpClient();
            if (token != null) {
                client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer",token.access_token);
            }

            return client[sendFunction](url,content)
                .Result.Content.ReadAsStringAsync()
                .Result;
        }

然后我可以将每个其他功能转换为一个衬里,如:

private string Post(string url,AuthenticationToken token = null) {
    this.Send(url,content,token,"PostAsync");
}

...如果我可以以安全的方式传递函数或函数名称,那将更好。

iCMS 回答:在C#中,是否可以重构Post和Put方法以消除代码重复?

通过Selvin的回复,我想出了一个办法:

        private string Post(string url,ByteArrayContent content,AuthenticationToken token = null) {
            return this.Send(token,(client) => client.PostAsync(url,content));
        }

        private string Put(string url,StringContent content,AuthenticationToken token) {
            return this.Send(token,(client) => client.PutAsync(url,content));
        }

        private string Send(AuthenticationToken token,Func<HttpClient,Task<HttpResponseMessage>> sendFunction) {
            ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;

            using HttpClient client = new HttpClient();
            if (token != null) {
                client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer",token.Access_token);
            }

            return sendFunction(client)
                .Result.Content.ReadAsStringAsync()
                .Result;
        }

...这几乎是我想要的,但是我仍然需要两次表达“客户”。

C#是否有任何符号可以让我删除此冗余?

还是我应该接受它为“效果最好”?

,

我认为由于某些原因您不能使用async/await运算符,

您可以这样减少冗余:

    public static class Ext
    {
        public static string Finalize(this Task<HttpResponseMessage> httpResponseMessage)
        {
            return httpResponseMessage
                .Result
                .Content
                .ReadAsStringAsync()
                .Result;
        }
    }

    public class Program
    {
        private string Post(string url,AuthenticationToken token = null)
        {
            return this.CreateClient(token)
                .PutAsync(url,content)
                .Finalize();
        }

        private string Put(string url,AuthenticationToken token)
        {
            return this.CreateClient(token)
                .PostAsync(url,content)
                .Finalize();
        }

        private HttpClient CreateClient(AuthenticationToken token)
        {

            ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;

            using HttpClient client = new HttpClient();
            if (token != null)
            {
                client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer",token.Value);
            }

            return client;
        }
    }

因此,将“客户端创建”包装在一种方法中,然后将“完成异步处理”包装到扩展方法中

,

您可以使用switch表达式。它在C#8中变得惊人地起作用。您可以在此处阅读更多内容并找到示例:

https://docs.microsoft.com/en-us/dotnet/csharp/whats-new/csharp-8#switch-expressions

更新:考虑使用枚举而不是函数名称来确保代码类型安全。

本文链接:https://www.f2er.com/1968483.html

大家都在问