代码随想录第48天|

#include
using namespace std;
int main(){
    int n,m,p1,p2,val;
    cin>>n>>m;
    vector> grid(n+1,vector(n+1,10005));
    for(int i=0;i>p1>>p2>>val;
        grid[p1][p2]=val;
        grid[p2][p1]=val;
    }
    //开始floyd
    for(int k=1;k<=n;k++){
        for(int i=1;i<=n;i++){
            for(int j=1;j<=n;j++){
                grid[i][j]=min(grid[i][j],grid[i][k]+grid[k][j]);
            }
        }
    }
    int z,start,end;
    cin>>z;
    while(z--){
         cin >> start >> end;
        if (grid[start][end] == 10005) cout << -1 << endl;
        else cout << grid[start][end] << endl;
    }
}
  • operator< 重载用于定义对象的默认排序规则,直接影响 STL 容器的排序行为。
  • operator() 重载用于自定义排序逻辑,通过将仿函数传递给 STL 容器来改变默认行为。
  • return k1.f > k2.f; // 小顶堆
  • #include
    #include
    #include
    using namespace std;
    int moves[1001][1001];
    int dir[8][2]={-2,-1,-2,1,-1,2,1,2,2,1,2,-1,1,-2,-1,-2};
    int b1, b2;
    // F = G + H
    // G = 从起点到该节点路径消耗
    // H = 该节点到终点的预估消耗
    
    struct Knight{
        int x,y;
        int g,h,f;
        bool operator < (const Knight & k) const{  // 重载运算符, 从小到大排序
         return k.f < f;
        }
    };
    
    priority_queue que;
    
    int Heuristic(const Knight& k) { // 欧拉距离
        return (k.x - b1) * (k.x - b1) + (k.y - b2) * (k.y - b2); // 统一不开根号,这样可以提高精度
    }
    void astar(const Knight& k)
    {
        Knight cur, next;
    	que.push(k);
    	while(!que.empty())
    	{
    		cur=que.top(); que.pop();
    		if(cur.x == b1 && cur.y == b2)
    		break;
    		for(int i = 0; i < 8; i++)
    		{
    			next.x = cur.x + dir[i][0];
    			next.y = cur.y + dir[i][1];
    			if(next.x < 1 || next.x > 1000 || next.y < 1 || next.y > 1000)
    			continue;
    			if(!moves[next.x][next.y])
    			{
    				moves[next.x][next.y] = moves[cur.x][cur.y] + 1;
    
                    // 开始计算F
    				next.g = cur.g + 5; // 统一不开根号,这样可以提高精度,马走日,1 * 1 + 2 * 2 = 5
                    next.h = Heuristic(next);
                    next.f = next.g + next.h;
                    que.push(next);
    			}
    		}
    	}
    }
    
    int main()
    {
        int n, a1, a2;
        cin >> n;
        while (n--) {
            cin >> a1 >> a2 >> b1 >> b2;
            memset(moves,0,sizeof(moves));
            Knight start;
            start.x = a1;
            start.y = a2;
            start.g = 0;
            start.h = Heuristic(start);
            start.f = start.g + start.h;
    		astar(start);
            while(!que.empty()) que.pop(); // 队列清空
    		cout << moves[b1][b2] << endl;
    	}
    	return 0;
    }

    启发式算法利用优先队列优先遍历某一顺序关键在于启发函数move数组用来及记录到达当前结点需要多少步 初始化为0 然后根据之前的+1.

你可能感兴趣的:(代码随想录,算法,c++,数据结构)