首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >管理巡航系统

管理巡航系统
EN

Code Review用户
提问于 2014-09-09 15:58:41
回答 2查看 695关注 0票数 5

跟进删除房间预订代码中的代码气味

该计划组织巡航,在其中设置船的舱室/房间。它还预订了客户信息和现有客房/房间的费用。

这是我的主要课程#:

代码语言:javascript
复制
    class Program
{
    static void Main(string[] args)
    {
        UBCruises bookings = new UBCruises ();
        Customer cust1 = new Customer ("Fred", "Johnstone", "A100356");
        Reservation booking = bookings.bookPassage("C", cust1, 2);       
        Console.WriteLine("Cust1's booking costs= {0}", booking.getCostofBooking());  //Astract Method from Reservation
        Console.Write ("Cabins booked are: ");
        ArrayList cabins = booking.cabins;
        for (int i = 0; i <  cabins.Count; i++)
            Console.Write ("{0}\t", ((room) cabins[i]).number);
        Console.WriteLine();
        Console.WriteLine();
        Customer cust2 = new Customer("Jane", "Jackson", "M892039");
        Reservation booking2 = bookings.bookPassage("H", cust2, 4);
        ///Console.WriteLine("Cust2's booking costs = {0}", booking2.cost);
        Console.WriteLine(booking2.getCostofBooking());
        Console.Write("Cabins booked are: ");
        cabins = booking2.cabins;
        for (int i = 0; i < cabins.Count; i++)
            Console.Write("{0}\t", ((room)cabins[i]).number);
        Console.WriteLine();
        Console.ReadLine();
    }
}

Customer

代码语言:javascript
复制
     public class Customer
{
    int discount = 1;
    String lastname, firstname;
    String accountNumber;

    public Customer(String firstname, String lastname, String accountNumber)
    {
        this.firstname = firstname;
        this.lastname = lastname;
        this.accountNumber = accountNumber;
    }
}

Reservation

代码语言:javascript
复制
    public class Reservation
{
    public Customer booker;
    public Boolean confirmed = true;
    public int cost;
    public ArrayList cabins = new ArrayList();

    public Reservation(Customer booker, Boolean confirmed)
    {
        this.booker = booker;
        this.confirmed = confirmed;
    }

    public Reservation(Customer booker, int cost, ArrayList cabins)
    {
        this.booker = booker;
        this.cost = cost;
        this.cabins = cabins;
    }

    public Reservation(Customer booker, int cost, room theCabin)
    {
        this.booker = booker;
        this.cost = cost;
        cabins.Add(theCabin);
    }
    public int getCostofBooking ()
    {
        return this.cost;
    }

}

Room

代码语言:javascript
复制
   public class room
{
    public int fare;
    public String number;
    public Boolean booked = false;

    public room(int fare, String number)
    {
        this.fare = fare;
        this.number = number;
    }
}

Ship

代码语言:javascript
复制
    public class Ship
{
    Dictionary<String, ArrayList> cabins = new Dictionary<String, ArrayList>();
    String name;

    public Ship(String name)
    {
        this.name = name;
        this.setupShip();
    }
    public void setupShip() // this method must belongs to SHip class.
    {


        ArrayList groupA = new ArrayList();
        for (int i = 0; i < 10; i++)
        {
            groupA.Add(new room(5000, "A" + (i + 1)));
        }

        ArrayList groupB = new ArrayList();
        for (int i = 0; i < 10; i++)
        {
            groupB.Add(new room(4000, "B" + (i + 1)));
        }

        ArrayList groupC = new ArrayList();
        for (int i = 0; i < 30; i++)
        {
            groupC.Add(new room(3500, "C" + (i + 1)));
        }

        ArrayList groupD = new ArrayList();
        for (int i = 0; i < 36; i++)
        {
            groupD.Add(new room(3400, "D" + (i + 1)));
        }

        ArrayList groupE = new ArrayList();
        for (int i = 0; i < 40; i++)
        {
            groupE.Add(new room(3300, "E" + (i + 1)));
        }

        ArrayList groupF = new ArrayList();
        for (int i = 0; i < 30; i++)
        {
            groupF.Add(new room(3400, "F" + (i + 1)));
        }

        ArrayList groupG = new ArrayList();
        for (int i = 0; i < 36; i++)
        {
            groupG.Add(new room(3300, "G" + (i + 1)));
        }

        ArrayList groupH = new ArrayList();
        for (int i = 0; i < 40; i++)
        {
            groupH.Add(new room(3200, "H" + (i + 1)));
        }

        addDeck("Balcony Suite", groupA);
        addDeck("Suite", groupB);
        addDeck("Deck 3 - Outside Twin", groupC);
        addDeck("Deck 2 - Outside Twin", groupD);
        addDeck("Deck 1 - Outside Twin", groupE);
        addDeck("Deck 3 - Inside Twin", groupF);
        addDeck("Deck 2 - Inside Twin", groupG);
        addDeck("Deck 1 - Inside Twin", groupH);
    } 

    public void addDeck(String deckName, ArrayList cabins)
    {
        this.cabins.Add(deckName, cabins);
    }

    public ArrayList getDeck(String deckName)
    {
        return (ArrayList)cabins[deckName];
    }
}

UBCruises

代码语言:javascript
复制
    public class UBCruises
{
    Ship ship1;

    public UBCruises()
    {
        ship1 = new Ship("Olympic Countess");
    }
    // Create instance of the ship and call the setupShip() from ship constructor.
      // setupShip() method

    public Reservation bookPassage(String cabinclass, Customer booker, int number)
    {
        ArrayList cabins;
        if (cabinclass.Equals("a", StringComparison.OrdinalIgnoreCase))
            cabins = ship1.getDeck("Balcony Suite");
        else if (cabinclass.Equals("b", StringComparison.OrdinalIgnoreCase))
            cabins = ship1.getDeck("Suite");
        else if (cabinclass.Equals("c", StringComparison.OrdinalIgnoreCase))
            cabins = ship1.getDeck("Deck 3 - Outside Twin");
        else if (cabinclass.Equals("d", StringComparison.OrdinalIgnoreCase))
            cabins = ship1.getDeck("Deck 2 - Outside Twin");
        else if (cabinclass.Equals("e", StringComparison.OrdinalIgnoreCase))
            cabins = ship1.getDeck("Deck 1 - Outside Twin");
        else if (cabinclass.Equals("f", StringComparison.OrdinalIgnoreCase))
            cabins = ship1.getDeck("Deck 3 - Inside Twin");
        else if (cabinclass.Equals("g", StringComparison.OrdinalIgnoreCase))
            cabins = ship1.getDeck("Deck 2 - Inside Twin");
        else 
            cabins = ship1.getDeck("Deck 1 - Inside Twin");
        if (available(cabins, number))
        {
            ArrayList bookedcabins = new ArrayList();
            int currentCabin = 0;
            int cost = 0;
            while (number > 0)
            {
                room thisCabin = (room)cabins[currentCabin];
                if (!thisCabin.booked)
                {
                    bookedcabins.Add(thisCabin);
                    cost += thisCabin.fare;
                    number--;
                }
                currentCabin++;
            }
            return new Reservation(booker, cost, bookedcabins);
        }
        else
            return new Reservation(booker, false);
    }

    public Boolean available(ArrayList cabins, int number)
    {
        int freeCount = 0;
        for (int i = 0; i < cabins.Count; i++)
        {
            if (!((room)cabins[i]).booked)
                freeCount++;
        }
        return number <= freeCount;
    }
}
}
EN

回答 2

Code Review用户

发布于 2014-09-09 18:23:40

初思

压痕

类上的缩进有点奇怪。它是一致的,所以我假设它是有意的,但我没有看到(在其他地方)有多少使用。除非有很强的理由,否则通常最好还是和大多数人一起去做这些事。

集合

有理由使用ArrayList而不是List<Room>吗?似乎有很多缺点,但没有好处。

公共领域

作为一般规则,在类的公共接口中不应该有字段。一个很好的例子是Reservation类中的小屋。它被初始化为一个新的ArrayList(),但由于它是公开的,没有任何安全网可以防止它被覆盖,清除任何先前预定的房间。

预期使用

从上到下,即使把它们变成属性也不能解决问题,如果我们只是让它们公开;设置;属性。如果预定的目的是为给定的客户,那么客户应该是一个只在构造时设置的read属性。

链式构造器

可能更多的是风格问题,而不是一个艰难的审查点,但我倾向于将多个构造函数链接到一个负责设置字段的构造函数上,而不是让多个ctors设置字段。这使得我们不太可能更改类,使某些ctors得到更新,而另一些则不会使创建的类处于无效状态。

代码语言:javascript
复制
public class Reservation {

    public Reservation(Customer booker, int cost, Room theCabin) 
      : Reservation (booker, cost, new []{theCabin}, false)  {}

    public Reservation(Customer booker, bool confirmed) 
      : Reservation (booker, 0, new []{}, confirmed)  {}

    public Reservation(Customer booker, int cost, IEnumerable<Room> theCabins, bool confirmed = false) {
        Booker = booker;
        Cost = cost;
        Cabins = theCabins.ToList();
    }

    public Customer Booker { get; private set;}
    public int Cost { get; private set;}
    public IEumerable<Room> Cabins { get; private set;} 

}    

系统与C#类型

除了AFAIK之外,我找不到权威的来源,建议使用C#类型(int、string、bool、float等)。相对于系统类型(整数、字符串、布尔、双)。我没有很强的理由来解释为什么会这样,但是我提到它,因为我们在代码String中有一个混合体,而不是string,但是int没有使用Integer。无论使用哪一套,我们都应该是一致的。

命名

类名应以大写Room (而不是room )开头,方法名称(如getCostOfBooking()setupShip() )也应如此。注意: SetupShip应该是私有的。外界没有必要知道这件事。

职责分离

Ship实际上只应该是房间的容器。初始化可以由它负责定义每个甲板上的房间的其他类(例如,ShipConfiguration)来执行。这使我们可以很容易地有不同的船舶布局。

舱室类和甲板的硬编码名称非常易碎。舱类到可用舱的映射应该是船舶配置的一部分,而不是BookPassage的一部分。把舱位递到船上,它应该能告诉你这种船舱是如何使用的。就目前情况而言,增加另一艘具有不同等级和甲板的船舶将是非常混乱的。根据一个人想要如何构造它,预订可以作为一个单一的操作进行。在船上订n个x级船舱,返回一个船舱的可枚举数或一个空的船舱(如果不够的话)。它可以通过多种方式进行调整,这取决于具体的使用要求,但重要的是封装可变的部件-将舱类映射到“甲板”,并让它对每艘船都是不同的。

票数 5
EN

Code Review用户

发布于 2014-09-11 00:23:47

看看您的代码,有几点想法:

客舱:

您可能应该考虑包括客户的联系信息,因为实际上,预订代理需要在预订完成后与客户联系。

折扣可以是任何金额还是你想要固定金额?如果是后者,保存这些值的字典可能会更容易维护,并且可以让您选择给折扣一个描述性的名称,并编辑您希望允许的名称。

预订班:

为预定的邮轮加上日期和描述性的名称是有意义的。这把你需要的信息放在一个地方。

船级:

因为您有很多代码分配房间给甲板,一个甲板类来容纳这些房间和一个集合甲板属于船,将大大有助于清理您的代码的那一部分。

票数 3
EN
页面原文内容由Code Review提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://codereview.stackexchange.com/questions/62432

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档