我对此代码有疑问。该程序旨在使用c ++中的深度优先搜索。我用Dev-Cpp,TurboC ++和visual studio。编译了它,并编写了exe文件。但它会在执行期间产生段错误。哪里有问题,我该怎么办?
#include <stdio.h>
#include <string.h>
#include <iostream.h>
#include <vector.h>
#include <deque.h>
using namespace std;
//Structure for Adding Edge to Graph
struct Neighbor
{
string Name;
int Distance;
int ShortestDistance;
};
//Class Data Structure for City type Node:
class City
{
public:
string Name;
City( );
City(string);
vector<Neighbor> Neighbors;
vector<Neighbor>::iterator NeighborNumber;
void AddNeighbor (string, int);
};
//Parameterless Class constructor
City::City( )
{
Name="";
NeighborNumber=Neighbors.begin( );
}
//Class Constructor with Name supplied:
City::City(string CityName)
{
Name=CityName;
NeighborNumber=Neighbors.begin( );
}
//Function or Method to Add Connected Node to City data structure
void City::AddNeighbor(string NeighborName, int NeighborDistance)
{
Neighbor TempNeighbor;
TempNeighbor.Name=NeighborName;
TempNeighbor.Distance=NeighborDistance;
Neighbors.push_back(TempNeighbor);
NeighborNumber=Neighbors.begin( );
}
//Data Structure for Entire Map
vector<City> Cities;
void MakeMap()
{
City TempCity;
//Enter data for Arad
TempCity.Name="Arad";
TempCity.Neighbors.clear();
TempCity.AddNeighbor("Zerind",75);
TempCity.AddNeighbor("Sibiu", 140);
TempCity.AddNeighbor("Timisoara",118);
Cities.push_back(TempCity);
//Enter data for Bucharest
TempCity.Name="Bucharest";
TempCity.Neighbors.clear();
TempCity.AddNeighbor("Giurgiu",90);
TempCity.AddNeighbor("Urziceni",85);
TempCity.AddNeighbor("Fagaras",211);
TempCity.AddNeighbor("Pitesti",101);
Cities.push_back(TempCity);
}
//Function to Display contents of Cities data structure to screen:
void PrintCities()
{
City TempCity;
Neighbor TempNeighbor;
vector<City>::iterator CityNumber;
//Loop Through Entire Cities vector
for(CityNumber=Cities.begin();CityNumber<Cities.end();CityNumber++)
{
TempCity=*CityNumber;
cout<<"Current City: "<<TempCity.Name<<endl;
cout<<"Neighbors: ";
//Loop Through Each Neighbor printing name and distance
for(TempCity.NeighborNumber=TempCity.Neighbors.begin();
TempCity.NeighborNumber<TempCity.Neighbors.end();
TempCity.NeighborNumber++)
{
TempNeighbor=*TempCity.NeighborNumber;
cout<<" "<<TempNeighbor.Name;
cout<<","<<TempNeighbor.Distance;
}
cout<<endl<<endl;
}
}
//Function to return Success or Failure on finding the Child Node given the
//Parent is a structure of type Neighbor. The ChildCity is returned by reference.
bool GetChildCity(Neighbor Parent, City* ChildCity)
{
City TempCity;
vector<City>::iterator CityNumber;
for(CityNumber=Cities.begin();CityNumber<Cities.end();CityNumber++)
{
TempCity=*CityNumber;
if(TempCity.Name==Parent.Name)
{
*ChildCity=TempCity;
return true;
}
}
return false;
}
class PathRecord
{
public:
string AccumulatedPath;
string LastEntry;
int AccumulatedDistance;
PathRecord(string);
void AddPath(PathRecord, City, Neighbor);
};
PathRecord::PathRecord(string Start)
{
AccumulatedPath=Start;
LastEntry=Start;
AccumulatedDistance=0;
}
void PathRecord::AddPath(PathRecord ParentRecord, City ChildCity, Neighbor CurrentNeighbor)
{
this->AccumulatedPath=ParentRecord.AccumulatedPath+" - "+ChildCity.Name;
this->LastEntry=ChildCity.Name;
this->AccumulatedDistance=ParentRecord.AccumulatedDistance+CurrentNeighbor.Distance;
}
vector<PathRecord> PathsTraveled;
//Perform Depth First Search giving Start Location and Ending Location
bool DepthFirstSearch(string StartName, string EndName)
{
City CurrentCity;
City StartCity;
City ChildCity;
City ExploredCity;
City FrontierCity;
Neighbor CurrentNeighbor;
bool StartCityFound=false;
bool GoalFound=false;
bool AlreadyExplored;
bool AlreadyInFrontier;
bool NewChildFound;
bool PathFound;
vector<City>::iterator CityNumber;
deque<City> Frontier;
deque<City> Explored;
deque<City>::iterator FrontierCityNumber;
deque<City>::iterator ExploredCityNumber;
PathRecord NewRecord(StartName);
PathRecord TemporaryRecord("");
vector<PathRecord>::iterator PathNumber;
if(StartName==EndName) return true;
if(StartName=="" || EndName == "") return false;
//*************************************************************************
// Search For Start
//*************************************************************************
for(CityNumber=Cities.begin();CityNumber<Cities.end();CityNumber++)
{
CurrentCity=*CityNumber;
if(CurrentCity.Name==StartName)
{
StartCity=CurrentCity;
StartCityFound=true;
}
}
if(StartCityFound==false) return false;
PathsTraveled.push_back(NewRecord);
Frontier.push_back(StartCity);
//*************************************************************************
// Search For Goal
//*************************************************************************
cout<<"\nRecording Exploratory Process:\n"<<"Start Location: "<<
StartName<<"\t Ending Location: "<<EndName<<endl;
//Get Next Location in the Frontier
while(!Frontier.empty() && GoalFound==false)
{
CurrentCity=Frontier.back();
cout<<"\nCurrent City: "<<CurrentCity.Name<<endl;
NewChildFound=false;
//Look through the Neighbors until an explored City is found.
while(CurrentCity.NeighborNumber<CurrentCity.Neighbors.end() && NewChildFound==false)
{
CurrentNeighbor=*CurrentCity.NeighborNumber;
cout<<"Current Neighbor: "<<CurrentNeighbor.Name<<endl;
if(GetChildCity(CurrentNeighbor, &ChildCity)==false)
{
cout<<"Didn't find a child\n";
return false;
}
if(ChildCity.Name==EndName)
{
cout<<"Goal Found\n";
GoalFound=true;
}
//Check for Child Already Explored
AlreadyExplored=false;
ExploredCityNumber=Explored.begin();
while(AlreadyExplored==false && ExploredCityNumber<Explored.end())
{
ExploredCity=*ExploredCityNumber;
if(ExploredCity.Name==ChildCity.Name) AlreadyExplored=true;
ExploredCityNumber++;
}
//Check for Child Already in Frontier
if(AlreadyExplored==false)
{
AlreadyInFrontier=false;
FrontierCityNumber=Frontier.begin();
while(AlreadyInFrontier==false && FrontierCityNumber<Frontier.end())
{
FrontierCity=*FrontierCityNumber;
if(FrontierCity.Name==ChildCity.Name) AlreadyInFrontier=true;
FrontierCityNumber++;
}
}
//Put the parent in the Frontier queue and Expand the Child Node
//Record the process in the Paths Traveled vector.
if(AlreadyExplored==false && AlreadyInFrontier==false)
{
Frontier.push_back(ChildCity);
NewChildFound=true;
PathNumber=PathsTraveled.begin( );
PathFound=false;
while(PathFound==false && PathNumber<PathsTraveled.end( ))
{
TemporaryRecord=*PathNumber;
if(TemporaryRecord.LastEntry==CurrentCity.Name)
{
NewRecord.AddPath(TemporaryRecord,
ChildCity, CurrentNeighbor);
PathsTraveled.push_back(NewRecord);
PathFound=true;
}
PathNumber++;
}
}
CurrentCity.NeighborNumber++;
}
//Display the Explored Queue on each pass
if(NewChildFound==false)
{
Explored.push_back(CurrentCity);
Frontier.pop_back();
}
cout<<"Explored: ";
for(ExploredCityNumber=Explored.begin();
ExploredCityNumber<Explored.end();ExploredCityNumber++)
{
ExploredCity=*ExploredCityNumber;
cout<<ExploredCity.Name<<" \t";
}
cout<<endl;
//Display the Frontier Queue on each pass
cout<<"Frontier: ";
for(FrontierCityNumber=Frontier.begin();
FrontierCityNumber<Frontier.end();FrontierCityNumber++)
{
FrontierCity=*FrontierCityNumber;
cout<<FrontierCity.Name<<" \t";
}
cout<<endl;
}
return GoalFound;
}
//Goal Path will print the path used to locate the Goal
//Supply the name of the goal after a search has been successful
void PrintGoalPath(string GoalName)
{
vector<PathRecord>::iterator PathNumber;
PathRecord TemporaryRecord("");
cout<<"\nGoal Path: "<<endl;
for(PathNumber=PathsTraveled.begin();PathNumber<PathsTraveled.end();PathNumber++)
{
TemporaryRecord=*PathNumber;
if(TemporaryRecord.LastEntry==GoalName)
cout<<TemporaryRecord.AccumulatedPath
<<" "<<TemporaryRecord.AccumulatedDistance<<endl;
}
cout<<endl;
}
//Program Starts here:
int main()
{
bool GoalFound;
MakeMap();
string StartLocation="Arad";
string GoalState="Bucharest";
GoalFound=DepthFirstSearch(StartLocation, GoalState);
if(GoalFound) PrintGoalPath(GoalState);
else cout<<"Couldn't Do It - "<<GoalState<<" is nowhere to be found!!\n";
return 0;
}
#include <stdio.h>
#include <string.h>
#include <iostream.h>
#include <vector.h>
#include <deque.h>
using namespace std;
//Structure for Adding Edge to Graph
struct Neighbor
{
string Name;
int Distance;
int ShortestDistance;
};
//Class Data Structure for City type Node:
class City
{
public:
string Name;
City( );
City(string);
vector<Neighbor> Neighbors;
vector<Neighbor>::iterator NeighborNumber;
void AddNeighbor (string, int);
};
//Parameterless Class constructor
City::City( )
{
Name="";
NeighborNumber=Neighbors.begin( );
}
//Class Constructor with Name supplied:
City::City(string CityName)
{
Name=CityName;
NeighborNumber=Neighbors.begin( );
}
//Function or Method to Add Connected Node to City data structure
void City::AddNeighbor(string NeighborName, int NeighborDistance)
{
Neighbor TempNeighbor;
TempNeighbor.Name=NeighborName;
TempNeighbor.Distance=NeighborDistance;
Neighbors.push_back(TempNeighbor);
NeighborNumber=Neighbors.begin( );
}
//Data Structure for Entire Map
vector<City> Cities;
void MakeMap()
{
City TempCity;
//Enter data for Arad
TempCity.Name="Arad";
TempCity.Neighbors.clear();
TempCity.AddNeighbor("Zerind",75);
TempCity.AddNeighbor("Sibiu", 140);
TempCity.AddNeighbor("Timisoara",118);
Cities.push_back(TempCity);
//Enter data for Bucharest
TempCity.Name="Bucharest";
TempCity.Neighbors.clear();
TempCity.AddNeighbor("Giurgiu",90);
TempCity.AddNeighbor("Urziceni",85);
TempCity.AddNeighbor("Fagaras",211);
TempCity.AddNeighbor("Pitesti",101);
Cities.push_back(TempCity);
}
//Function to Display contents of Cities data structure to screen:
void PrintCities()
{
City TempCity;
Neighbor TempNeighbor;
vector<City>::iterator CityNumber;
//Loop Through Entire Cities vector
for(CityNumber=Cities.begin();CityNumber<Cities.end();CityNumber++)
{
TempCity=*CityNumber;
cout<<"Current City: "<<TempCity.Name<<endl;
cout<<"Neighbors: ";
//Loop Through Each Neighbor printing name and distance
for(TempCity.NeighborNumber=TempCity.Neighbors.begin();
TempCity.NeighborNumber<TempCity.Neighbors.end();
TempCity.NeighborNumber++)
{
TempNeighbor=*TempCity.NeighborNumber;
cout<<" "<<TempNeighbor.Name;
cout<<","<<TempNeighbor.Distance;
}
cout<<endl<<endl;
}
}
//Function to return Success or Failure on finding the Child Node given the
//Parent is a structure of type Neighbor. The ChildCity is returned by reference.
bool GetChildCity(Neighbor Parent, City* ChildCity)
{
City TempCity;
vector<City>::iterator CityNumber;
for(CityNumber=Cities.begin();CityNumber<Cities.end();CityNumber++)
{
TempCity=*CityNumber;
if(TempCity.Name==Parent.Name)
{
*ChildCity=TempCity;
return true;
}
}
return false;
}
class PathRecord
{
public:
string AccumulatedPath;
string LastEntry;
int AccumulatedDistance;
PathRecord(string);
void AddPath(PathRecord, City, Neighbor);
};
PathRecord::PathRecord(string Start)
{
AccumulatedPath=Start;
LastEntry=Start;
AccumulatedDistance=0;
}
void PathRecord::AddPath(PathRecord ParentRecord, City ChildCity, Neighbor CurrentNeighbor)
{
this->AccumulatedPath=ParentRecord.AccumulatedPath+" - "+ChildCity.Name;
this->LastEntry=ChildCity.Name;
this->AccumulatedDistance=ParentRecord.AccumulatedDistance+CurrentNeighbor.Distance;
}
vector<PathRecord> PathsTraveled;
//Perform Depth First Search giving Start Location and Ending Location
bool DepthFirstSearch(string StartName, string EndName)
{
City CurrentCity;
City StartCity;
City ChildCity;
City ExploredCity;
City FrontierCity;
Neighbor CurrentNeighbor;
bool StartCityFound=false;
bool GoalFound=false;
bool AlreadyExplored;
bool AlreadyInFrontier;
bool NewChildFound;
bool PathFound;
vector<City>::iterator CityNumber;
deque<City> Frontier;
deque<City> Explored;
deque<City>::iterator FrontierCityNumber;
deque<City>::iterator ExploredCityNumber;
PathRecord NewRecord(StartName);
PathRecord TemporaryRecord("");
vector<PathRecord>::iterator PathNumber;
if(StartName==EndName) return true;
if(StartName=="" || EndName == "") return false;
//*************************************************************************
// Search For Start
//*************************************************************************
for(CityNumber=Cities.begin();CityNumber<Cities.end();CityNumber++)
{
CurrentCity=*CityNumber;
if(CurrentCity.Name==StartName)
{
StartCity=CurrentCity;
StartCityFound=true;
}
}
if(StartCityFound==false) return false;
PathsTraveled.push_back(NewRecord);
Frontier.push_back(StartCity);
//*************************************************************************
// Search For Goal
//*************************************************************************
cout<<"\nRecording Exploratory Process:\n"<<"Start Location: "<<
StartName<<"\t Ending Location: "<<EndName<<endl;
//Get Next Location in the Frontier
while(!Frontier.empty() && GoalFound==false)
{
CurrentCity=Frontier.back();
cout<<"\nCurrent City: "<<CurrentCity.Name<<endl;
NewChildFound=false;
//Look through the Neighbors until an explored City is found.
while(CurrentCity.NeighborNumber<CurrentCity.Neighbors.end() && NewChildFound==false)
{
CurrentNeighbor=*CurrentCity.NeighborNumber;
cout<<"Current Neighbor: "<<CurrentNeighbor.Name<<endl;
if(GetChildCity(CurrentNeighbor, &ChildCity)==false)
{
cout<<"Didn't find a child\n";
return false;
}
if(ChildCity.Name==EndName)
{
cout<<"Goal Found\n";
GoalFound=true;
}
//Check for Child Already Explored
AlreadyExplored=false;
ExploredCityNumber=Explored.begin();
while(AlreadyExplored==false && ExploredCityNumber<Explored.end())
{
ExploredCity=*ExploredCityNumber;
if(ExploredCity.Name==ChildCity.Name) AlreadyExplored=true;
ExploredCityNumber++;
}
//Check for Child Already in Frontier
if(AlreadyExplored==false)
{
AlreadyInFrontier=false;
FrontierCityNumber=Frontier.begin();
while(AlreadyInFrontier==false && FrontierCityNumber<Frontier.end())
{
FrontierCity=*FrontierCityNumber;
if(FrontierCity.Name==ChildCity.Name) AlreadyInFrontier=true;
FrontierCityNumber++;
}
}
//Put the parent in the Frontier queue and Expand the Child Node
//Record the process in the Paths Traveled vector.
if(AlreadyExplored==false && AlreadyInFrontier==false)
{
Frontier.push_back(ChildCity);
NewChildFound=true;
PathNumber=PathsTraveled.begin( );
PathFound=false;
while(PathFound==false && PathNumber<PathsTraveled.end( ))
{
TemporaryRecord=*PathNumber;
if(TemporaryRecord.LastEntry==CurrentCity.Name)
{
NewRecord.AddPath(TemporaryRecord,
ChildCity, CurrentNeighbor);
PathsTraveled.push_back(NewRecord);
PathFound=true;
}
PathNumber++;
}
}
CurrentCity.NeighborNumber++;
}
//Display the Explored Queue on each pass
if(NewChildFound==false)
{
Explored.push_back(CurrentCity);
Frontier.pop_back();
}
cout<<"Explored: ";
for(ExploredCityNumber=Explored.begin();
ExploredCityNumber<Explored.end();ExploredCityNumber++)
{
ExploredCity=*ExploredCityNumber;
cout<<ExploredCity.Name<<" \t";
}
cout<<endl;
//Display the Frontier Queue on each pass
cout<<"Frontier: ";
for(FrontierCityNumber=Frontier.begin();
FrontierCityNumber<Frontier.end();FrontierCityNumber++)
{
FrontierCity=*FrontierCityNumber;
cout<<FrontierCity.Name<<" \t";
}
cout<<endl;
}
return GoalFound;
}
//Goal Path will print the path used to locate the Goal
//Supply the name of the goal after a search has been successful
void PrintGoalPath(string GoalName)
{
vector<PathRecord>::iterator PathNumber;
PathRecord TemporaryRecord("");
cout<<"\nGoal Path: "<<endl;
for(PathNumber=PathsTraveled.begin();PathNumber<PathsTraveled.end();PathNumber++)
{
TemporaryRecord=*PathNumber;
if(TemporaryRecord.LastEntry==GoalName)
cout<<TemporaryRecord.AccumulatedPath
<<" "<<TemporaryRecord.AccumulatedDistance<<endl;
}
cout<<endl;
}
//Program Starts here:
int main()
{
bool GoalFound;
MakeMap();
string StartLocation="Arad";
string GoalState="Bucharest";
GoalFound=DepthFirstSearch(StartLocation, GoalState);
if(GoalFound) PrintGoalPath(GoalState);
else cout<<"Couldn't Do It - "<<GoalState<<" is nowhere to be found!!\n";
return 0;
}
答案 0 :(得分:2)
段错误意味着您已尝试访问超出段边界的内存,可能是代码或数据段。
错误是:
矢量迭代器不兼容
为什么?
因为您已经将数组从A复制到B,但是您想使用A.begin()迭代器与B的迭代器进行比较,并且这不会在Visual Studio中传递编译器的兼容性检查,
void _Compat(const _Myiter& _Right) const
{ // test for compatible iterator pair
if (this->_Getcont() == 0
|| this->_Getcont() != _Right._Getcont())
{ // report error
_DEBUG_ERROR("vector iterators incompatible");
_SCL_SECURE_INVALID_ARGUMENT;
}
}
所以我的建议是,不要试图保存指向向量的迭代器开始,你可以在需要时使用临时迭代器
进一步的建议,系统地学习C ++,除非你有足够的信心,否则不要按照你的想法编写代码。
来吧,努力工作,你可以做到!