DUPE:C#中"使用"的使用
我见过人们使用以下内容,我想知道它的目的是什么?这样对象在垃圾收集后被破坏了吗?
例:
using (Something mySomething = new Something()) {
mySomething.someProp = "Hey";
}
Run Code Online (Sandbox Code Playgroud) 在Visual Studio 2008 C#中,如果我创建一个新类,默认情况下会显示以下命名空间,并且每次都会手动删除它们.是否有设置/文件夹模板,我可以去除这些不需要的命名空间,使其不出现在项目中创建的每个新类上?
使用System.Collections.Generic; 使用System.Linq; 使用System.Text;
前几天在代码审查期间出现了一个关于 using 块应该多快关闭的问题。一个阵营说,“一旦你完成了对象”;另一个,“在它超出范围之前的某个时间”。
在这个特定的例子中,有一个 DataTable 和一个 SqlCommand 对象要处理。我们需要在单个语句中引用两者,并且需要迭代 DataTable。
营地1:
List<MyObject> listToReturn = new List<MyObject>();
DataTable dt = null;
try
{
using (InHouseDataAdapter inHouseDataAdapter = new InHouseDataAdapter())
using (SqlCommand cmd = new SqlCommand())
{
dt = inHouseDataAdapter.GetDataTable(cmd);
}
foreach (DataRow dr in dt.Rows)
{
listToReturn.Add(new MyObject(dr));
}
}
finally
{
if (dt != null)
{
dt.Dispose();
}
}
Run Code Online (Sandbox Code Playgroud)
推理:在使用完 SqlCommand 后立即处理它。不要在另一个对象的 using 块中开始可能很长的操作,例如迭代表。
营地2:
List<MyObject> listToReturn = new List<MyObject>();
using (InHouseDataAdapter inHouseDataAdapter = new InHouseDataAdapter())
using (SqlCommand cmd = new …Run Code Online (Sandbox Code Playgroud) 我已经阅读了几篇关于using语句的文章,试图了解何时应该使用它.这听起来像大多数人认为它应该尽可能多地使用,因为它可以保证处理未使用的物体.
问题是所有的例子总是显示如下:
using (SqlCommand scmFetch = new SqlCommand())
{
// code
}
Run Code Online (Sandbox Code Playgroud)
这是有道理的,但它只是一小段代码.在数据库上执行查询时应该怎么做?所有步骤是什么?它看起来像这样:
string sQuery = @"
SELECT [ID], [Description]
FROM [Zones]
ORDER BY [Description] ";
DataTable dtZones = new DataTable("Zones");
using (SqlConnection scnFetchZones = new SqlConnection())
{
scnFetchZones.ConnectionString = __sConnectionString;
scnFetchZones.Open();
using (SqlCommand scmdFetchZones = new SqlCommand())
{
scmdFetchZones.Connection = scnFetchZones;
scmdFetchZones.CommandText = sQuery;
using (SqlDataAdapter sdaFetch = new SqlDataAdapter())
{
sdaFetch.SelectCommand = scmdFetchZones;
sdaFetch.Fill(dtZones);
}
}
if (scnFetchZones.State == ConnectionState.Open)
scnFetchZones.Close();
}
Run Code Online (Sandbox Code Playgroud)
我想知道的是:
•是否可以使用4,5,10个嵌套的using语句来确保处理所有对象?
•我在什么时候做错了什么,我应该考虑修改吗?
•如果由于嵌套的using语句太多而需要修订,我有哪些选择? …
我正在调用第三方库,其中有很多类实现了IDisposable.
我是否需要在所有这些模式上使用模式?
使用或使用try/catch内部的正确方法try/catch是什么?
using (SqlConnection connection = CreateSqlConnection(connString))
{
using (SqlCommand command = CreateSqlCommand()
{
try{//open connection + execute command + do something else}
catch{//do something}
}
}
Run Code Online (Sandbox Code Playgroud)
与
try
{
using (SqlConnection connection = CreateSqlConnection(connString))
{
using (SqlCommand command = CreateSqlCommand()
{
//open connection + execute command + do something else
}
}
}
catch
{
//do something
}
Run Code Online (Sandbox Code Playgroud) 我总是理所当然地运行“删除和排序使用” ,因为这似乎是正确的做法。但现在我开始想:我们为什么要这样做?
当然,干净和紧凑的代码总是有好处的。如果 MS 花时间将其作为 VS 中的菜单项,一定会有一些好处。
谁能回答:为什么要这样做?删除和/或排序使用对编译时或运行时(或其他)有哪些好处?
我创建了一个自定义范围访问器(它只是返回 DefaultLifetimeScope),以便能够添加自定义范围的生活方式。然后该组件被注册为
Component
.For<..>
.LifestyleScoped<CustomScope>()
Run Code Online (Sandbox Code Playgroud)
但是,我不知道如何实际启动新的 CustomScope 范围/生命周期。该文档显示使用开始一个新范围
using (Container.BeginScope()) {
// ..
}
Run Code Online (Sandbox Code Playgroud)
但我的目标是创建/开始/启动特定范围,而不是通用LifestyleScoped()注册。新的作用域应该只影响显式注册到 CustomScope 的组件;不是通用范围组件或针对其他范围生活方式注册的组件。
开始(我的自定义范围)范围/生命周期的过程是什么?
请链接至相关文档;正如我所问,因为我无法轻易找到它。该代码使用Castle Windsor 3.3。
背景:
我来自 Autofac,正在寻找相当于每个匹配生命周期范围的实例来在 EF 上下文上建立 UoW。“每个请求”可能有多个 UoW,并且不同的存储库可能有不同的 UoW - 我还希望将来支持嵌套。
虽然有很多文章讨论创建 UoW 模式,但它们[全部]都与某些上下文(例如 HTTP 或 WFC 请求)绑定(错误地,IMOHO) - 而这不是这个问题的目的。我特别感兴趣的是如何启动一个自定义作用域,该作用域向下流过调用图并“存在于”using 块内。
笔记:
BoundTo()(和LifestyleBoundTo()/ )生活方式LifestyleBoundToNearest()与对象图相反(并且需要改变类型),并且切换到这样的生活方式严格来说并不是这个问题的解决方案/答案。但是,如果能为他们提供一个好的案例..
scope castle-windsor using-statement inversion-of-control castle-windsor-3
我最近在 using 语句中遇到了异常处理问题。问题是在“使用块”中抛出的异常可能会被吞掉,例如看代码:
class DisposableObject : IDisposable
{
public void Dispose()
{
throw new Exception("dispose");
}
}
class Program
{
static void Main()
{
try
{
using (var obj = new DisposableObject())
{
throw new Exception("using");
}
}
catch(Exception ex)
{
Console.WriteLine(ex.Message);
}
}
}
Run Code Online (Sandbox Code Playgroud)
在此示例中,您将在输出中看到 'dispose',第一个异常将被忽略,您将永远不会知道它。经过一番搜索,我找到了关于使用块的常见错误的文章https://msdn.microsoft.com/en-us/library/aa355056(v=vs.110).aspx。但我的问题不是关于如何避免异常吞咽,我想知道为什么 MS 决定使用 block 来解包
try
{
...
}
finally
{
}
Run Code Online (Sandbox Code Playgroud)
而不是其他的,例如他们可以解开使用这样的东西:
//this code prevents exception swallowing
try
{
...
}
catch (Exception ex)
{
try
{
if (obj != null) …Run Code Online (Sandbox Code Playgroud) 我想使用基类的模板函数,如下所示:
struct A {
template <class T> static auto f() { \*code*\ }
};
template <class A_type> struct B : public A_type {
using A_type::f;
void g() { auto n = f<int>(); }
};
Run Code Online (Sandbox Code Playgroud)
但是,这不会编译。
error: expected '(' for function-style cast or type
construction
void g() { auto n = f<int>(); }
~~~^
error: expected expression
void g() { auto n = f<int>(); }
Run Code Online (Sandbox Code Playgroud)
但是直接引用基类而不是模板确实有效:
struct A {
template <class T> static auto f() { \*code*\ }
};
template <class …Run Code Online (Sandbox Code Playgroud) using-statement ×10
c# ×6
.net ×5
idisposable ×2
c++ ×1
exception ×1
inheritance ×1
linq ×1
namespaces ×1
performance ×1
scope ×1
sql ×1
templates ×1