codecamp

C++ 一个更合理的距离矩阵

虽然这段代码可以工作,但它本可以组织的更好。既然我们已经写了一个原型,那么我们就处于评价其设计并改进之的有利位置了。

那现在的代码有些什么问题呢?

  1. 我们提前不知道要创建多大的距离矩阵,所以我们选择了一个任意大的数字(50),然后创建了一个固定大小的矩阵。更好的方式是允许距离矩阵以类似Set的方式扩充,而apmatrix类的resize函数使之成为可能。

  2. 矩阵中的数据没有很好的封装。我们不得不以城市名的集合与矩阵本身作为参数传给processLine,这样很不合适。再就是,因为我们没提供执行错误检查的访问函数,所以使用距离矩阵容易出错。有个好的想法是,将表示城市名的Set对象和表示距离的apmatrix对象组合到DistMatrix类中。

下面是DistMatrix类头文件大概形式的一个草稿:

class DistMatrix {
private:
  Set cities;
  apmatrix<int> distances;

public:
  DistMatrix (int rows);

  void add (const apstring& city1, const apstring& city2, int dist);
  int distance (int i, int j) const;
  int distance (const apstring& city1, const apstring& city2) const;
  apstring cityName (int i) const;
  int numCities () const;
  void print ();
};

我们可以使用这个接口来简化main函数:

void main ()
{
  apstring line;
  ifstream infile ("distances");
  DistMatrix distances (2);

  while (true) {
    getline (infile, line);
    if (infile.eof()) break;
    processLine (line, distances);
  }

  distances.print ();
}

也可以简化 processLine函数:

void processLine (const apstring& line, DistMatrix& distances)
{
  char quote = ’\"’;
  apvector<int> quoteIndex (4);
  quoteIndex[0] = line.find (quote);
  for (int i=1; i<4; i++) {
    quoteIndex[i] = find (line, quote, quoteIndex[i-1]+1);
  }

  // 将行分割为子串
  int len1 = quoteIndex[1] - quoteIndex[0] - 1;
  apstring city1 = line.substr (quoteIndex[0]+1, len1);
  int len2 = quoteIndex[3] - quoteIndex[2] - 1;
  apstring city2 = line.substr (quoteIndex[2]+1, len2);
  int len3 = line.length() - quoteIndex[2] - 1;
  apstring distString = line.substr (quoteIndex[3]+1, len3);
  int distance = convertToInt (distString);

  // 将新数据添加到距离矩阵中
  distances.add (city1, city2, distance);
}

我把实现DistMatrix类的成员函数留作练习请读者完成。

C++ 距离矩阵
C++ 术语表
温馨提示
下载编程狮App,免费阅读超1000+编程语言教程
取消
确定
目录

关闭

MIP.setData({ 'pageTheme' : getCookie('pageTheme') || {'day':true, 'night':false}, 'pageFontSize' : getCookie('pageFontSize') || 20 }); MIP.watch('pageTheme', function(newValue){ setCookie('pageTheme', JSON.stringify(newValue)) }); MIP.watch('pageFontSize', function(newValue){ setCookie('pageFontSize', newValue) }); function setCookie(name, value){ var days = 1; var exp = new Date(); exp.setTime(exp.getTime() + days*24*60*60*1000); document.cookie = name + '=' + value + ';expires=' + exp.toUTCString(); } function getCookie(name){ var reg = new RegExp('(^| )' + name + '=([^;]*)(;|$)'); return document.cookie.match(reg) ? JSON.parse(document.cookie.match(reg)[2]) : null; }