求问一道 C#笔试题,想知道最好的解答是什么

2020-09-16 20:28:02 +08:00
 richards64

题目如下:

这是一段用于计算多个几何形状面积之和的程序

  1. 指出程序段存在的不妥之处,并重构代码
  2. 在 1 的基础上增加一种可计算的几何形状类型三角形,其面积为 底×高×1/2
public class Shape
{
    public int Type { get; set; }
    public int Radius { get; set; }
    public int Width { get; set; }
    public int Length { get; set; }
}

public class ShapeCalculator
{
    public static double CalculateTotalArea(List<Shape> shapes)
    {
        double totalArea = 0;
        if (shapes != null && shapes.Count() > 0)
        {
            foreach (Shape shape in shapes)
            {
                if (shape.Type == 1)
                {
                    totalArea += Math.PI * shape.Radius * shape.Radius;
                }
                else if (shape.Type == 2)
                {
                    totalArea += shape.Length * shape.Width;
                }
            }
        }
        return totalArea;
    }
}

我的回答是这样的:

interface ICalc
{
    double GetAera();
}

class Circle : ICalc
{
    public int Radius { get; set; }

    public double GetAera()
    {
        return Math.PI * Radius * Radius;
    }
}

class Rectangle : ICalc
{
    public int Length { get; set; }
    public int Width { get; set; }

    public double GetAera()
    {
        return Length * Width;
    }
}

class Triangle : ICalc
{
    public int Bottom { get; set; }
    public int Height { get; set; }

    public double GetAera()
    {
        return Bottom * Height * 0.5;
    }
}

class ShapeCalculator
{
    public static double CalculateTotalArea(List<ICalc> shapes)
    {
        double totalArea = 0;
        if (shapes != null)
        {
            totalArea = shapes.Sum(shape => shape.GetAera());
        }
        return totalArea;
    }
}

凭我的水平和理解能力就只有写到这种程度了……有什么更好的写法吗?

2732 次点击
所在节点    程序员
16 条回复
across
2020-09-16 21:28:51 +08:00
我猜原意不止 oop,还要你改几个细节,比如 int 应该是 float,面积 float 精度就足够。
forgottencoast
2020-09-16 23:05:26 +08:00
源代码最主要的问题就是每增加一个 Shape,都要改动 CalculateTotalArea 方法。
写法很多,你这个写法可以了。
剩下的就是细节问题了,比如#1 所说的,Width 和 Length 用 int 肯定不妥。
CalculateTotalArea 接收的参数类型要更抽象一点,List<T>肯定不好。
你定义的接口 ICalc 命名太宽,和方法名 GetArea 不够匹配。
richards64
2020-09-16 23:30:34 +08:00
@forgottencoast CalculateTotalArea(IEnumerable<ICalc> shapes) 好一点?
andrewpsy
2020-09-17 00:15:59 +08:00
上面都说的很好了,还有个可能是面试官想测你知不知道 strategy pattern 。你要是想 over engineering 可以实现一下玩玩。
richards64
2020-09-17 00:38:58 +08:00
@andrewpsy 实际情况是面试官好像对我的回答没有什么异议,对我的 C#基础还是挺满意的,但是最后拒掉了我的理由是因为这个岗位需要精通 SQL 优化,这我就不会了……
yazoox
2020-09-17 08:29:05 +08:00
这就是“十动然拒”?
奇怪,如果岗位是对 SQL 技能有特别需求,一开始知道你不会(比如:简历),那还面试啥?这不是浪费大家时间么?
Rwing
2020-09-17 08:48:50 +08:00
挺好的,我觉得 HR 只是不想招人,换公司继续面吧
forgottencoast
2020-09-17 09:28:48 +08:00
@richards64 #3
是的。
越抽象的接口适用范围越广,如果你用不到更具体接口的其他成员,就应该用更抽象的接口。
IEnumerable<T>是最抽象的接口了,所有的泛型集合都实现了它,一般设计时可以考虑先用它,除非它不符合需求,再考虑更具体的接口。
yamatamain
2020-09-17 09:35:36 +08:00
@richards64 总会有一个理由。
SWALLOWW
2020-09-17 09:45:43 +08:00
第一眼 shapes.Count()有问题...
beingWH
2020-09-17 09:57:28 +08:00
感觉问题不大。
beingWH
2020-09-17 10:11:35 +08:00
```
interface ICalc
{
float GetAera();
}

class Circle : ICalc
{
public float Radius { get; set; }

public float GetAera()
{
return Math.PI * Radius * Radius;
}
}

class Rectangle : ICalc
{
public float Length { get; set; }
public float Width { get; set; }

public float GetAera()
{
return Length * Width;
}
}

class Triangle : ICalc
{
public float Bottom { get; set; }
public float Height { get; set; }

public float GetAera()
{
return Bottom * Height * 0.5;
}
}

static class ShapeCalculator
{
public static float CalculateTotalArea(this List<ICalc> shapes)
{
float totalArea = 0;
if (shapes != null)
{
totalArea = shapes.Sum(shape => shape.GetAera());
}
return totalArea;
}
}
```
kop1989
2020-09-17 10:20:37 +08:00
我有个想法不知道对不对。

觉得可以在你的基础上再添加一个 Shape 转换为 ICalc 实现类的逻辑。
因为从实际项目的角度讲,你再怎么重构,数据源也是不变的。
你这个重构最终丢了逻辑。既你把 ICalc 的实现类抉择抛给了调用 CalculateTotalArea 的人。
原来的数据源是 List<Shape>。现在传进来的还应该是 List<Shape>。
Caskia
2020-09-17 10:55:52 +08:00
@richards64 拒绝的问题应该不在你这个回答上面,敢问这是哪家的面试题?
richards64
2020-09-17 16:20:10 +08:00
@kop1989 这个没太看明白,能具体演示一下吗
richards64
2020-09-17 16:23:43 +08:00
@Caskia 确实挺奇怪的,我看 JD 上有要求掌握 WPF 就投了简历,简历上也表示出了我只有 WPF 经历,然后就让我去面试了,去了之后发现实际的主要工作内容是.NET Core 的后端开发,只是个别项目组有少量的老旧项目涉及到 WPF

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/707685

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX