Questions tagged «c#»

C#是Microsoft与.NET平台并行创建的一种多范式,托管的,垃圾回收的面向对象编程语言。

7
如果函数必须在执行预期的行为之前执行null检查,这是不好的设计吗?
所以我不知道这是好是坏的代码设计,所以我想我最好问一下。 我经常创建用于处理涉及类的数据的方法,并且经常对方法进行大量检查,以确保事先没有空引用或其他错误。 一个非常基本的例子: // fields and properties private Entity _someEntity; public Entity SomeEntity => _someEntity; public void AssignEntity(Entity entity){ _someEntity = entity; } public void SetName(string name) { if (_someEntity == null) return; //check to avoid null ref _someEntity.Name = name; label.SetText(_someEntity.Name); } 因此,您可以看到im每次都检查null。但是该方法应该没有此检查吗? 例如,外部代码应事先清除数据,这样方法就不需要进行如下验证: if(entity != null) // this …
67 c#  design  validation 

10
向下转换的正确用法是什么?
向下转换意味着从基类(或接口)转换为子类或叶类。 如果您从转换System.Object为其他类型,则可能会导致沮丧。 向下转换不受欢迎,可能有代码味道:例如,面向对象的理论更喜欢定义和调用虚拟或抽象方法,而不是向下转换。 什么是向下转换的好用例(如果有)?也就是说,在什么情况下编写向下转换的代码是合适的? 如果您的答案为“无”,那么为什么该语言支持向下转换?

16
程序员在选择语言和框架时应有多少自由度?
我开始在一家主要面向C#的公司工作。我们有些人喜欢Java和JRuby,但是这里的大多数程序员都喜欢C#。我之所以被录用,是因为我有很多构建Web应用程序的经验,并且因为我倾向于JRuby on Rails或nodejs等较新的技术。 我最近开始了一个构建Web应用程序的项目,该项目的重点是在短时间内完成很多工作。软件负责人指示我使用mvc4而不是rails。可能还可以,除了我不知道mvc4,我不懂C#,而且我是唯一负责创建Web应用程序服务器和前端UI的人。 使用我已经非常了解的框架(Rails)而不是使用mvc4有意义吗?该决定背后的原因是,技术负责人不了解Jruby / rails,因此无法重用代码。 相反的论点: 他不会为代码做贡献,坦率地说, 这个项目不需要他。因此,他是否知道JRuby / rails并不重要。 实际上,我们可以重用代码,因为我们有很多Java应用程序,JRuby可以从中提取代码,反之亦然。实际上,他已经投入了一些资源将Java库转换为C#,而不仅仅是在JRuby on Rails应用程序上运行Java库。都是因为他不喜欢Java或JRuby 我已经构建了许多Web应用程序,但是使用一些陌生的东西会引起一些混乱,而我却无法像过去那样在短时间内构建出色的应用程序。这样很好 学习新技术在这一领域很重要。问题是,对于这个项目,我们需要快速完成很多工作。 在什么时候应该允许开发人员选择其工具?这取决于公司吗?我的公司吮吸或认为这正常吗?是否存在绿色牧场?我看错了方向吗?

12
验证其参数的构造函数是否违反SRP?
我试图尽可能地遵守单一职责原则(SRP),并且习惯了某种严重依赖委托的特定模式(对于方法上的SRP)。我想知道这种方法是否合理,或者是否存在严重问题。 例如,要检查对构造函数的输入,我可以引入以下方法(Stream输入是随机的,可以是任何东西) private void CheckInput(Stream stream) { if(stream == null) { throw new ArgumentNullException(); } if(!stream.CanWrite) { throw new ArgumentException(); } } 这种方法(可以说)做的不止一件事 检查输入 引发不同的异常 因此,为了遵守SRP,我将逻辑更改为 private void CheckInput(Stream stream, params (Predicate<Stream> predicate, Action action)[] inputCheckers) { foreach(var inputChecker in inputCheckers) { if(inputChecker.predicate(stream)) { inputChecker.action(); } } } 据说哪件事只会做一件事(是吗?):检查输入。对于输入的实际检查和异常的抛出,我介绍了类似的方法 bool …

12
有一个标志来指示是否应该抛出错误
我最近开始在一个与一些年龄较大的开发人员(大约50岁以上)一起工作的地方。他们致力于处理无法解决系统故障的航空关键应用。结果,较老的程序员倾向于以这种方式进行编码。 他倾向于在对象中放入一个布尔值,以指示是否应该引发异常。 例 public class AreaCalculator { AreaCalculator(bool shouldThrowExceptions) { ... } CalculateArea(int x, int y) { if(x < 0 || y < 0) { if(shouldThrowExceptions) throwException; else return 0; } } } (在我们的项目中,该方法可能会失败,因为我们正在尝试使用当时无法使用的网络设备。区域示例仅是异常标志的示例) 对我来说,这似乎是一种代码气味。编写单元测试变得有些复杂,因为每次都必须测试异常标志。另外,如果出现问题,您是否想立即知道?确定如何继续是呼叫者的责任吗? 他的逻辑/理由是我们的程序需要做一件事,向用户显示数据。任何其他不会阻止我们这样做的异常都应忽略。我同意不应忽视它们,而应该冒泡并由适当的人员来处理,而不必为此处理标志。 这是处理异常的好方法吗? 编辑:只是为了提供更多有关设计决策的信息,我怀疑这是因为如果该组件失败,程序仍可以运行并完成其主要任务。因此,当用户可以正常工作时,我们不想抛出异常(不处理它?)并让它删除程序。 编辑2:为了提供更多上下文,在本例中,该方法被调用来重置网卡。当网卡断开连接并重新连接时,会出现问题,它被分配了另一个IP地址,因此Reset将引发异常,因为我们将尝试使用旧的IP重置硬件。

11
如何使老板相信ANSI C不适合我们的新项目?[关闭]
几个月前,我们开始开发一个应用程序,以控制内部开发的测试设备并记录一组测量值。它应该具有简单的UI,并且由于必须进行连续记录,因此可能需要线程。该应用程序将使用几年,并且在此期间应由许多计算机科学专业的学生维护。 我们的老板大约30年前毕业(不要被视为冒犯;我也有一半以上的时间都在我的背上),并责令我们在ANSI C中开发此应用程序。理由是他是唯一的一位将一直存在,因此他必须能够了解我们在做什么。他还裁定我们不应使用抽象数据类型。他甚至给我们列出了他希望我们使用的全局变量的名称(叹气)。 我实际上尝试了这种方法一段时间,但确实让我放慢了脚步,以确保所有指针操作都是安全的并且所有字符串的大小均正确。此外,与手头问题实际相关的代码行数仅占我们代码库的一小部分。几天后,我放弃了整个工作,并使用C#重新开始。我们的老板已经看到了程序的运行,他喜欢它的工作方式,但是他不知道该程序是用另一种语言编写的。 下周,我们两个人将开会讨论源代码,以便他“知道如何维护它”。我有点害怕,我想听听你们可以用哪些论点支持我的决定。 ward弱的你

5
显式或隐式实现接口有什么区别?
在Visual Studio中,我可以右键单击一个接口,然后选择“实现接口”或“明确实现接口”。 public class Test : ITest { public string Id // Generated by Implement Interface { get { throw new NotImplementedException(); } } string ITest.Id // Generated by Implement Interface Explicitly { get { throw new NotImplementedException(); } } } 我看到的两者之间的唯一区别是,如果选择显式实现接口,则在创建接口属性和方法时会将接口名称添加到接口属性和方法中。 我发现它使代码更具可读性,因为我可以看到该方法/属性的来源,但是这对使用或编译该类的方式有什么不同吗?我隐式或显式实现接口真的重要吗?
64 c#  syntax 

11
大布尔表达式比分解成谓词方法的同一个表达式更具可读性吗?[关闭]
什么更容易理解,一个大的布尔语句(相当复杂),或同一语句分解为谓词方法(很多额外的代码需要阅读)? 选项1,大布尔表达式: private static bool ContextMatchesProp(CurrentSearchContext context, TValToMatch propVal) { return propVal.PropertyId == context.Definition.Id && !repo.ParentId.HasValue || repo.ParentId == propVal.ParentId && ((propVal.SecondaryFilter.HasValue && context.SecondaryFilter.HasValue && propVal.SecondaryFilter.Value == context.SecondaryFilter) || (!context.SecondaryFilter.HasValue && !propVal.SecondaryFilter.HasValue)); } 选项2,条件分为谓词方法: private static bool ContextMatchesProp(CurrentSearchContext context, TValToMatch propVal) { return MatchesDefinitionId(context, propVal) && MatchesParentId(propVal) && (MatchedSecondaryFilter(context, propVal) …
63 c#  readability 

11
该类设计是否违反单一责任原则?
今天我和某人吵架。 我正在解释使用富域模型相对于贫血域模型的好处。我用一个简单的类演示了我的观点: public class Employee { public Employee(string firstName, string lastName) { FirstName = firstName; LastName = lastname; } public string FirstName { get private set; } public string LastName { get; private set;} public int CountPaidDaysOffGranted { get; private set;} public void AddPaidDaysOffGranted(int numberOfdays) { // Do stuff } …


6
为什么C#是用不同于Java的“ new”和“ virtual + override”关键字构成的?
在Java中没有virtual,new,override对于方法定义的关键字。因此,方法的工作很容易理解。因为如果DerivedClass扩展BaseClass的和具有相同的名称和它们的签名的方法BaseClass的那么压倒一切将发生在运行时多态性(提供的方法是不是static)。 BaseClass bcdc = new DerivedClass(); bcdc.doSomething() // will invoke DerivedClass's doSomething method. 现在来到C#时,可能会有太多的困惑,并且很难理解newor virtual+derive或new +虚拟重写的工作方式。 我不明白为什么在世界上为什么要在我的方法中添加一个DerivedClass具有相同名称和签名的方法,BaseClass并定义一个新的行为,但是在运行时多态时,BaseClass将调用该方法!(这不是覆盖,但在逻辑上应该覆盖)。 如果virtual + override逻辑实现是正确的,则程序员必须考虑在编码时应允许用户重写的方法。里面有一些有利条件(让我们现在不去那里)。 那么,为什么在C#中有如此大的空间用于非逻辑推理和混乱。所以,我可以重新塑造我的问题是在现实世界方面,我应该考虑使用virtual + override替代new,还可以使用的new,而不是virtual + override? 在获得了特别是Omar的一些非常好的回答之后,我发现C#设计人员更加强调程序员在创建方法之前应该思考的问题,这种方法很好并且可以处理Java中的一些菜鸟错误。 现在我想到一个问题。就像在Java中,如果我有类似的代码 Vehicle vehicle = new Car(); vehicle.accelerate(); 后来我提出新的类SpaceShip衍生Vehicle。然后我想将所有内容更改car为一个SpaceShip对象,而我只需要更改一行代码 Vehicle vehicle = new SpaceShip(); vehicle.accelerate(); 这不会在任何代码点破坏我的任何逻辑。 但是在C#的情况下,如果SpaceShip不覆盖Vehicle类accelerate并使用,new则代码的逻辑将被破坏。这不是不利条件吗?

17
为什么使用OO方法而不是巨大的“ switch”语句?
我在.Net,C#商店工作,并且我有一位同事一直坚持认为,我们应该在代码中使用带有大量“案例”而不是更多面向对象方法的巨型Switch语句。他的论断始终可以回溯到以下事实:Switch语句会编译为“ cpu跳转表”,因此是最快的选择(即使在其他情况下,我们的团队被告知我们不在乎速度)。 老实说,我对此没有争议……因为我不知道他在说什么。 是吗 他只是在说他的屁股吗? 只是想在这里学习。

7
您如何用C#或类似Java的语言编码代数数据类型?
代数数据类型很容易解决一些问题,例如,列表类型可以非常简洁地表示为: data ConsList a = Empty | ConsCell a (ConsList a) consmap f Empty = Empty consmap f (ConsCell a b) = ConsCell (f a) (consmap f b) l = ConsCell 1 (ConsCell 2 (ConsCell 3 Empty)) consmap (+1) l 这个特定的例子在Haskell中,但是在其他语言中,本机支持代数数据类型,这将是相似的。 事实证明,有一个明显的面向对象样式子类型的映射:数据类型成为抽象基类,每个数据构造函数都成为具体的子类。这是Scala中的示例: sealed abstract class ConsList[+T] { def map[U](f: T …

9
可读性与可维护性,编写嵌套函数调用的特殊情况
我的嵌套函数调用的编码样式如下: var result_h1 = H1(b1); var result_h2 = H2(b2); var result_g1 = G1(result_h1, result_h2); var result_g2 = G2(c1); var a = F(result_g1, result_g2); 我最近转到了一个部门,该部门非常使用以下编码样式: var a = F(G1(H1(b1), H2(b2)), G2(c1)); 我的编码方式的结果是,在功能崩溃的情况下,Visual Studio可以打开相应的转储并指出发生问题的行(我特别担心访问冲突)。 我担心,如果因第一种方式编程的相同问题而导致崩溃,我将无法知道是哪个函数导致了崩溃。 另一方面,行上进行的处理越多,一页上得到的逻辑就越多,从而增强了可读性。 我的恐惧是正确的还是我缺少什么?总的来说,在商业环境中这是首选吗?可读性还是可维护性? 我不知道它是否相关,但是我们正在使用C ++(STL)/ C#。

6
我们是否应该为所有请求创建一个新的HttpClient单一实例?
最近,我从asp.net monsters上看到了此博客文章,该文章讨论了HttpClient以下使用方式的问题: using(var client = new HttpClient()) { } 根据博客文章,如果我们HttpClient在每个请求之后都处理掉它,则可以使TCP连接保持打开状态。这有可能导致System.Net.Sockets.SocketException。 每个帖子的正确方法是创建一个实例,HttpClient因为它有助于减少套接字的浪费。 从帖子: 如果我们共享HttpClient的单个实例,则可以通过重用套接字来减少套接字的浪费: namespace ConsoleApplication { public class Program { private static HttpClient Client = new HttpClient(); public static void Main(string[] args) { Console.WriteLine("Starting connections"); for(int i = 0; i<10; i++) { var result = Client.GetAsync("http://aspnetmonsters.com").Result; Console.WriteLine(result.StatusCode); } Console.WriteLine("Connections done"); …
57 c#  http-request 

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.