在C#中正确使用"using"的方法

3

我有以下两组代码。我的问题是我们需要为命令和适配器使用“using”吗,还是只需为连接使用?正确的做法是什么?

 using (OracleConnection conn = new OracleConnection(ConnectionString))
    {
        conn.Open();
        OracleCommand command = new OracleCommand(ProcedureName)
        {
            CommandType = CommandType.StoredProcedure,
            Connection = conn
        };
        command.Parameters.Add(new OracleParameter("P_ID", OracleDbType.Varchar2, Id, ParameterDirection.Input));
        command.Parameters.Add(new OracleParameter("CUR_OUT", OracleDbType.RefCursor, ParameterDirection.Output));

        OracleDataAdapter adapter = new OracleDataAdapter(command);
        adapter.Fill(dt);
    }

上面的代码只有一个using语句,而下面的代码有三个using语句。
 using (OracleConnection conn = new OracleConnection(ConnectionString))
    {
        await conn.OpenAsync();
        using (OracleCommand oCommand = new OracleCommand(ProcedureName))
        {
            oCommand.BindByName = true;
            oCommand.CommandType = CommandType.StoredProcedure;
            oCommand.CommandTimeout = await GetCommandTimeout(DatabaseConstants.OracleCommandTimeoutInSeconds);
            oCommand.Connection = conn;

            oCommand.Parameters.Add(new OracleParameter("P_ID", OracleDbType.Varchar2, Id, ParameterDirection.Input));
            oCommand.Parameters.Add(new OracleParameter("CUR_OUT", OracleDbType.RefCursor, ParameterDirection.Output));
            using (OracleDataAdapter oDatAdapter = new OracleDataAdapter(oCommand))
            {
                oDatAdapter.Fill(dataSet);
            }
        }
    }

你可以将 using 应用于任何实现 IDisposable 接口的对象上,这个接口基本上是 try-finally 语句的一个包装器。 - Kunal Mukherjee
3
越多越好。 - Uwe Keim
你可以使用using,也可以显式调用dispose。使用using更安全,因为这样就不会忘记释放资源。而且看起来更好。using实际上是插入了一个try-catch-finally块,在其中的catch块为空,在finally块中调用dispose。并非所有可IDisposable对象都需要被处理。例如SqlConnection只需关闭并让其超出范围即可。处理可以防止在关闭后重新打开它,这是唯一的区别。再次强调,使用using更安全,这样就不会忘记关闭连接。 - FalcoGer
2个回答

6

您需要它们来进行连接和评论。任何实现IDisposable接口的内容都应该被处理。

在创建命令之前,不需要先打开连接。这意味着您可以跳过一组{}。

using (for connection)
using (for command)
{
processing
}

这样格式化起来更加美观、简单。

我建议在开始时就检查是否可以添加适配器的 using 语句。

同时请注意,在当前 C# 版本(8.0 在此编写)中,您可以对变量声明使用 using 语句。

using var conn = new OracleConnection()

没有()。变量在最后被处理掉。这意味着格式更少。这被称为 "using声明" - https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/proposals/csharp-8.0/using


关于跳过大括号{},我认为最好总是将它们写出来并明确说明。但这是一个风格问题,每个人都必须自己找到答案或遵守公司规定。 - FalcoGer
并不总是这样。我经常在一行接着一行使用 using using using,因为如果你有7-8个带有{}的using和多行代码,那么缩进就会变得非常混乱 - 缩进太多了。 - TomTom
@Chatra 它实现了 IDisposable 接口吗?如果是,那就是的。 - LarsTech
@TomTom我没有看到DataAdapert在这里实现IDisposable。我有什么遗漏吗?https://learn.microsoft.com/en-us/dotnet/api/system.data.oracleclient.oracledataadapter?view=netframework-4.8 - Chatra
他的意思是组件(Component),它是一个类。链接?是你给我们提供的。看看那里的继承层级 - 除了过时之外,该类经过 System.ComponentModel.Component。 - TomTom
显示剩余5条评论

0

您可以在所有实现IDisposable接口的对象上使用using

  • 如果这些对象由.NET框架管理,那么在使用完它们后会显式调用销毁它们。
  • 如果它们不是由.NET框架管理的,则需要手动处理以释放它们。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接