2023-05-19:汽车从起点出发驶向目的地,该目的地位于出发位置东面 target 英里处。 沿途有加油站,每个 station[i] 代表一个加油站, 它位于出发位置东面 station[i][
2023-05-19:汽车从起点出发驶向目的地,该目的地位于出发位置东面 target 英里处。
沿途有加油站,每个 station[i] 代表一个加油站,
它位于出发位置东面 station[i][0] 英里处,并且有 station[i][1] 升汽油。
假设汽车油箱的容量是无限的,其中最初有 startFuel 升燃料。
它每行驶 1 英里就会用掉 1 升汽油。
当汽车到达加油站时,它可能停下来加油,将所有汽油从加油站转移到汽车中。
为了到达目的地,汽车所必要的最低加油次数是多少?如果无法到达目的地,则返回 -1 。
注意:如果汽车到达加油站时剩余燃料为 0,它仍然可以在那里加油。
如果汽车到达目的地时剩余燃料为 0,仍然认为它已经到达目的地。
输入:target = 100, startFuel = 10, stations = [[10,60],[20,30],[30,30],[60,40]]。
输出:2。
答案2023-05-19:
具体步骤如下:
1.初始化车内油量 to 和已经加得次数 cnt。
2.遍历所有加油站,对于每个加油站,判断能否到达。如果不能到达,就从大根堆中不断取出油量添加到车内,直至可以到达该加油站或无法再添加油量为止。如果无法到达该加油站,则无法到达目标位置,返回-1。
3.如果能够到达该加油站,则将该加油站的油量添加到大根堆中,并继续向前移动。
4.如果无法到达目标位置,则不断从大根堆中取出油量,直至能够到达目标位置或者大根堆为空为止。
5.返回已经加油的次数。
时间复杂度:O(nlogn),其中n为加油站的数量。主要是因为该算法使用了堆来维护加油站的油量,每次需要考虑哪个加油站的油量最多,以便优先选择加油量最大的加油站。
空间复杂度:O(n),其中n为加油站的数量。主要是因为该算法使用了堆存储加油站的油量,所以需要额外的空间存储堆中的元素。
go完整代码如下:
package main
import (
"container/heap"
)
func minRefuelStops(target int, startFuel int, stations [][]int) int {
if startFuel >= target {
return 0
}
// 大根堆
// 维持的是:最值得加油的加油站,有多少油
// 最值得:加得次数少,跑的还最远
h := &IntHeap{}
heap.Init(h)
// 当前车里的油,能达到的位置
to := startFuel
cnt := 0
for _, station := range stations {
position := station[0]
fuel := station[1]
if to < position {
for !h.IsEmpty() && to < position {
to += heap.Pop(h).(int)
cnt++
if to >= target {
return cnt
}
}
if to < position {
return -1
}
}
heap.Push(h, fuel)
}
// 最后一个加油站的位置,都达到了
// 但还没有到target
for !h.IsEmpty() {
to += heap.Pop(h).(int)
cnt++
if to >= target {
return cnt
}
}
return -1
}
func main() {
target := 100
startFuel := 10
stations := [][]int{{10, 60}, {20, 30}, {30, 30}, {60, 40}}
result := minRefuelStops(target, startFuel, stations)
println(result)
}
// IntHeap实现大根堆
type IntHeap []int
func (h IntHeap) Len() int {
return len(h)
}
func (h IntHeap) Less(i, j int) bool {
return h[i] > h[j]
}
func (h IntHeap) Swap(i, j int) {
h[i], h[j] = h[j], h[i]
}
func (h *IntHeap) Push(x interface{}) {
*h = append(*h, x.(int))
}
func (h *IntHeap) Pop() interface{} {
n := len(*h)
x := (*h)[n-1]
*h = (*h)[:n-1]
return x
}
func (h *IntHeap) IsEmpty() bool {
return h.Len() == 0
}

rust完整代码如下:
use std::collections::BinaryHeap;
fn min_refuel_stops(target: i32, start_fuel: i32, stations: Vec<Vec<i32>>) -> i32 {
if start_fuel >= target {
return 0;
}
// 大根堆
// 维持的是:最值得加油的加油站,有多少油
// 最值得:加得次数少,跑的还最远
let mut heap = BinaryHeap::new();
// 当前车里的油,能达到的位置
let mut to = start_fuel as i64;
let mut cnt = 0;
for station in stations.iter() {
let position = station[0] as i64;
let fuel = station[1] as i64;
if to < position {
while !heap.is_empty() && to < position {
to += heap.pop().unwrap();
cnt += 1;
if to >= target as i64 {
return cnt;
}
}
if to < position {
return -1;
}
}
heap.push(fuel);
}
// 最后一个加油站的位置,都达到了
// 但还没有到target
while !heap.is_empty() {
to += heap.pop().unwrap();
cnt += 1;
if to >= target as i64 {
return cnt;
}
}
-1
}
fn main() {
let target = 100;
let start_fuel = 10;
let stations = vec![vec![10, 60], vec![20, 30], vec![30, 30], vec![60, 40]];
let result = min_refuel_stops(target, start_fuel, stations);
println!("{}", result);
}

c语言完整代码如下:
#include <stdio.h>
#include <stdlib.h>
// IntHeap实现大根堆,这里用函数指针代替仿函数
int cmp(int a, int b) {
return a < b;
}
// 交换两个数的值
void swap(int* a, int* b) {
int temp = *a;
*a = *b;
*b = temp;
}
typedef struct IntHeap {
int (*cmp)(int, int);
void (*swap)(int*, int*);
int* data;
int size;
int capacity;
}IntHeap;
// 初始化大根堆
void initHeap(IntHeap* heap, int (*cmp)(int, int)) {
heap->cmp = cmp;
heap->swap = &swap;
heap->data = (int*)malloc(sizeof(int) * 128);
heap->size = 0;
heap->capacity = 128;
}
// 扩容
void resize(IntHeap* heap) {
int newCapacity = heap->capacity * 2;
int* newData = (int*)realloc(heap->data, sizeof(int) * newCapacity);
heap->data = newData;
heap->capacity = newCapacity;
}
// 堆化
void down(IntHeap* heap, int i) {
while (i * 2 + 1 < heap->size) {
int left = i * 2 + 1;
int right = i * 2 + 2;
int j = left;
if (right < heap->size && heap->cmp(heap->data[right], heap->data[left])) {
j = right;
}
if (heap->cmp(heap->data[i], heap->data[j])) {
break;
}
heap->swap(&heap->data[i], &heap->data[j]);
i = j;
}
}
// 入堆
void pushHeap(IntHeap* heap, int val) {
if (heap->size == heap->capacity) {
resize(heap);
}
heap->data[heap->size++] = val;
int i = heap->size - 1;
while (i > 0) {
int p = (i - 1) / 2;
if (heap->cmp(heap->data[p], heap->data[i])) {
break;
}
heap->swap(&heap->data[p], &heap->data[i]);
i = p;
}
}
// 弹出堆顶元素
int popHeap(IntHeap* heap) {
int top = heap->data[0];
heap->data[0] = heap->data[--heap->size];
down(heap, 0);
return top;
}
int minRefuelStops(int target, int startFuel, int** stations, int stationsSize, int* stationsColSize) {
if (startFuel >= target) {
return 0;
}
// 大根堆
// 维持的是:最值得加油的加油站,有多少油
// 最值得:加得次数少,跑的还最远
IntHeap heap;
initHeap(&heap, &cmp);
// 当前车里的油,能达到的位置
long long to = startFuel;
int cnt = 0;
for (int i = 0; i < stationsSize; i++) {
int position = stations[i][0];
int fuel = stations[i][1];
if (to < position) {
while (heap.size && to < position) {
to += popHeap(&heap);
cnt++;
if (to >= target) {
return cnt;
}
}
if (to < position) {
return -1;
}
}
pushHeap(&heap, fuel);
}
// 最后一个加油站的位置,都达到了
// 但还没有到 target
while (heap.size) {
to += popHeap(&heap);
cnt++;
if (to >= target) {
return cnt;
}
}
return -1;
}
int main() {
int target = 100;
int startFuel = 10;
int** stations = (int**)malloc(sizeof(int*) * 4);
int stationsColSize[4] = { 2, 2, 2, 2 };
for (int i = 0; i < 4; i++) {
stations[i] = (int*)malloc(sizeof(int) * 2);
}
stations[0][0] = 10;
stations[0][1] = 60;
stations[1][0] = 20;
stations[1][1] = 30;
stations[2][0] = 30;
stations[2][1] = 30;
stations[3][0] = 60;
stations[3][1] = 40;
int result = minRefuelStops(target, startFuel, stations, 4, stationsColSize);
printf("%d\n", result);
for (int i = 0; i < 4; i++) {
free(stations[i]);
}
free(stations);
return 0;
}

c++完整代码如下:
#include <iostream>
#include <vector>
#include <queue>
using namespace std;
// IntHeap实现大根堆
struct IntHeap {
bool operator()(int a, int b) { return a < b; }
};
int minRefuelStops(int target, int startFuel, vector<vector<int>>& stations) {
if (startFuel >= target) {
return 0;
}
// 大根堆
// 维持的是:最值得加油的加油站,有多少油
// 最值得:加得次数少,跑的还最远
priority_queue<int, vector<int>, IntHeap> heap;
// 当前车里的油,能达到的位置
long long to = startFuel;
int cnt = 0;
for (auto station : stations) {
int position = station[0];
int fuel = station[1];
if (to < position) {
while (!heap.empty() && to < position) {
to += heap.top();
heap.pop();
cnt++;
if (to >= target) {
return cnt;
}
}
if (to < position) {
return -1;
}
}
heap.push(fuel);
}
// 最后一个加油站的位置,都达到了
// 但还没有到target
while (!heap.empty()) {
to += heap.top();
heap.pop();
cnt++;
if (to >= target) {
return cnt;
}
}
return -1;
}
int main() {
int target = 100;
int startFuel = 10;
vector<vector<int>> stations = { {10, 60}, {20, 30}, {30, 30}, {60, 40} };
int result = minRefuelStops(target, startFuel, stations);
cout << result << endl;
return 0;
}

2023-05-19:汽车从起点出发驶向目的地,该目的地位于出发位置东面 target 英里处。 沿途有加油站,每个 station[i] 代表一个加油站, 它位于出发位置东面 station[i][的更多相关文章
- 2023 01 19 HW
2023 01 19 HW Okay, then let's start. Okay. Maybe Karina, we start with the C2 design freeze. Yeah, ...
- [LeetCode] Minimize Max Distance to Gas Station 最小化去加油站的最大距离
On a horizontal number line, we have gas stations at positions stations[0], stations[1], ..., statio ...
- 【转载】Spring Boot【快速入门】2019.05.19
原文出处:https://www.cnblogs.com/wmyskxz/p/9010832.html Spring Boot 概述 Build Anything with Spring Boot ...
- Perl: hash散列转换为Json报错集, perl.c,v $$Revision: 4.0.1.8 $$Date: 1993/02/05 19:39:30 $
bash-2.03$ ./u_json.pl Can't locate object method "encode" via package "JSON" at ...
- 2016/05/19 thinkphp 3.2.2 文件上传
显示效果: 多文件上传. 这里是两个文件一起上传 上传到文件夹的效果: ①aa为调用Home下common文件夹下的function.php 中的rname方法 实现的 ②cc为调用与Home ...
- 【转载】Spring学习(1)——快速入门--2019.05.19
原文地址:https://www.cnblogs.com/wmyskxz/p/8820371.html 认识 Spring 框架 Spring 框架是 Java 应用最广的框架,它的成功来源于理念 ...
- Fitness - 05.19
倒计时226天 运动45分钟,共计9组,4.7公里.拉伸10分钟. 每组跑步3分钟(6.5KM/h),走路2分钟(5.5KM/h). 上周的跑步计划中断了,本周重复第三阶段的跑步计划. 一共掉了10斤 ...
- [Swift]LeetCode871. 最低加油次数 | Minimum Number of Refueling Stops
A car travels from a starting position to a destination which is target miles east of the starting p ...
- LeetCode 871 - 最低加油次数 - [贪心+优先队列]
汽车从起点出发驶向目的地,该目的地位于出发位置东面 target 英里处. 沿途有加油站,每个 station[i] 代表一个加油站,它位于出发位置东面 station[i][0] 英里处,并且有 s ...
- LeetCode之Weekly Contest 93
第一题:二进制间距 问题: 给定一个正整数 N,找到并返回 N 的二进制表示中两个连续的 1 之间的最长距离. 如果没有两个连续的 1,返回 0 . 示例 1: 输入:22 输出:2 解释: 22 的 ...
随机推荐
- 文心一言 VS 讯飞星火 VS chatgpt (106)-- 算法导论10.1 4题
四.用go语言,重写 ENQUEUE 和 DEQUEUE 的代码,使之能处理队列的下溢和上溢. 文心一言: 在 Go 语言中,我们可以使用切片来实现队列.下面是如何实现 ENQUEUE 和 DEQUE ...
- Android项目Library导入的问题整理
Android项目Library导入的问题整理 本来帮助朋友找寻一下android的一些特效的demo,结果找到了一个,朋友试验可以,自己却是在导入项目需要的library的时候总是出问题,真的很是丢 ...
- javascript 如何开启调试功能
目录 javascript 如何开启调试功能 方式一: 打开浏览器,点击源码,直接点击一个,就加上断点了 (基于浏览器) 方式二: 打开代码,在 js 中加入 debugger 关键字,就加上断点了( ...
- 21. 从零用Rust编写正反向代理,tokio竟然这样对待socket!
wmproxy wmproxy已用Rust实现http/https代理, socks5代理, 反向代理, 静态文件服务器,四层TCP/UDP转发,内网穿透,后续将实现websocket代理等,会将实现 ...
- svn的常规使用
svn的常规使用 svn的常规使用 1 客户端 2 svn server 3 qt使用svn 4 svn项目迁移 Ubuntu上使用svn 1 安装 2 使用 svn的常规使用 1 客户端 下载地址: ...
- Windows上的多jdk版本管理工具
前言 Java在Windows上因为版本太多导致难以管理,这个项目可以很好的解决这点 项目地址 GitHub - ystyle/jvms: JDK Version Manager (JVMS) for ...
- [Python急救站课程]输出水仙花数
python #d = 0 print("所有三位数中的水仙花数如下所示:") for i in range(100, 1000): a = i // 100 # 求百位数 b = ...
- Vue一些进阶知识-基于官网(笔记)
前言 主要根据vue官网文档完成.对一些平时可能会用到的知识.组件进行收集,为的是对vue的可用性有一个大致的了解.博客中的组件介绍可能只涉及简单用法,完整用法还是以官网为准. 基础 启动过程: 主文 ...
- NLP技术如何为搜索引擎赋能
在全球化时代,搜索引擎不仅需要为用户提供准确的信息,还需理解多种语言和方言.本文详细探讨了搜索引擎如何通过NLP技术处理多语言和方言,确保为不同地区和文化的用户提供高质量的搜索结果,同时提供了基于Py ...
- 避免defer陷阱:拆解延迟语句,掌握正确使用方法
基本概念 Go语言的延迟语句defer有哪些特点?通常在什么情况下使用? Go语言的延迟语句(defer statement)具有以下特点: 延迟执行:延迟语句会在包含它的函数执行结束前执行,无论函数 ...