< 每日算法 - JavaScript解析:获取最小展台数量 >

在这里插入图片描述

👉 一. 任务描述:

力扣嘉年华将举办一系列展览活动,后勤部将负责为每场展览提供所需要的展台。 已知后勤部得到了一份需求清单,记录了近期展览所需要的展台类型, demand[i][j] 表示第 i 天展览时第 j 个展台的类型。 在满足每一天展台需求的基础上,请返回后勤部需要准备的 最小 展台数量。

注意

  • 同一展台在不同天中可以重复使用。

  • 1 <= demand.length,demand[i].length <= 100

  • demand[i][j] 仅为小写字母

/**
 * @param {string[]} demand
 * @return {number}
 */
var minNumBooths = function(demand) {
	...
}

本题取自 leetcode 秋赛题集

》 示例一:

输入:demand = ["acd","bed","accd"]

输出:6

解释

  • 第 0 天需要展台 a、c、d;
  • 第 1 天需要展台 b、e、d;
  • 第 2 天需要展台 a、c、c、d;(由于c类型展台同一天最少需要两台,所以取最大数量)

因此,后勤部准备 abccde 共 6台展台,可以满足每天的展览需求;

》示例二

输入:demand = ["abc","ab","ac","b"]

输出:3

解释:abc每种类型展台任意一天使用台数不超过1台,故只需要 abc各一台。

👉 二. 题意解析

根据题目,可以思考得出,因为限制了 demand[i][j] 仅为小写字母,可以定义两个长度为26的一维数组变量。

一个用于存储全局每种类型的展台所需要使用的台数;另外一个,用于存储每天(局部)中,每种类型展台使用台数,通过比较全局和局部的展台数量,取最多所需的展台数量进行存储。

解题思路
通过 new Array(26).fill(0)去创建26个字母类型的展台存储数组,通过循环对应天数的展台使用情况,记录每天的使用次数进行比对(Math.max(todayTimes, allTimes)

其中,有一个知识点需要记录下,str.charCodeAt(index) 这个函数,它会返回你给定str[index]字符对应的UTF-8编码。 而因为限制的原因,恰好可以通过 type.charCodeAt() - 97 的方式,获取对应展台类型的位置,进行记录!

具体知识点,可以通过拓展知识去了解。


拓展知识

charCodeAt() 方法可返回指定位置的字符的 UTF-8 编码。这个返回值是 0 - 65535 之间的整数。

方法 charCodeAt()charAt() 方法执行的操作相似,只不过前者返回的是位于指定位置的字符的编码,而后者返回的是字符子串。

例子

let str = 'abc'

console.log(str.charCodeAt(0)) // returns 97:"a"
console.log(str.charCodeAt(1)) // returns 98:"b"
console.log(str.charCodeAt(2)) // returns 99:"c"

详细点击跳转 👉 UTF-8 C0 控制与基本的 Latin(拉丁字母)
👈

详细点击跳转 👉 String.charCodeAt() 函数 / JavaScript charCodeAt() 方法👈


👉三. 解决方案 ( 如果看不懂,可以配合代码来看,有注释 )

/**
 * @param {string[]} demand
 * @return {number}
 */
var minNumBooths = function(demand) {
    // 方法一 (未改良过,但是思路正确)

    // 汇总所有类型展台
    let enumCase = [...new Set(demand.join('').split(''))]
    
    for(let showcaseList of demand) {
        let showTimes = {}
        for(let type of showcaseList.split('')) {
            showTimes[type] = showTimes[type] !== undefined ? (showTimes[type] + 1) : 1
            showTimes[type] > enumCase.filter(item => item === type).length && enumCase.push(type)
        }
    }

    return enumCase.length

    // -------优化前后---------

    // 方法二 (改良过,速度快)

    // 总共有26种字母,出题的限制(demand[i][j] 仅为小写字母)
    /* 如果类型可能是数字或者单个文字,那么方法不如第一种好用。
    不过数据不是死的,如果实际运用,肯定是让数据更加明确,比如用二维数组来传入。如: 
    
    [
        ['展台a', '展台2', '展台e', '展台1', '展台5'],
        ['展台6', '展台22', '展台e', '展台1', '展台y'],
        ...
    ]

    这样子,那么用第一种方法就更加合适了
    
    */
    
    let allTypeTimes = new Array(26).fill(0)

    for(let showcaseList of demand) {
        let currentTypeTimes = new Array(26).fill(0)
        for(let type of showcaseList.split('')) {
            // 通过charCodeAt获取的是字符对于的UTF-8的对应编码,而因为限制,所有类型均为小写字母
            // a 为 起点, UTF-8中,a = 97, 'a'.charCodeAt() = 97 - 97 = 0,
            // 和我们一开始定义的大小为26的数值数组对应上,作为每天每种类型展示需要次数存储的变量
            currentTypeTimes[type.charCodeAt() - 97] += 1

            // 运用Math.max取全局和局部的展示台使用最大台数
            allTypeTimes[type.charCodeAt() - 97] = Math.max(currentTypeTimes[type.charCodeAt() - 97], allTypeTimes[type.charCodeAt() - 97])
        }
    }

    return Array.from(allTypeTimes).reduce((prev, cur) => prev + cur)
};

往期内容 💨

🔥 < 每日算法 - Javascript解析:经典弹珠游戏 >

🔥 < 每日算法 - JavaScript解析:从尾到头打印链表 >

🔥 < JavaScript技术分享: 大文件切片上传 及 断点续传思路 >

🔥 < 每日知识点:关于Javascript 精进小妙招 ( Js技巧 ) >

  • 3
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论
以下是使用C++实现会议安排问题的贪心算法示例代码: ```cpp #include <iostream> #include <vector> #include <algorithm> // 定义会议结构体 struct Meeting { int start; int end; }; // 比较函数,按照会议结束时间升序排序 bool compare(Meeting m1, Meeting m2) { return m1.end < m2.end; } // 贪心算法实现会议安排 std::vector<Meeting> scheduleMeetings(std::vector<Meeting>& meetings) { // 按照结束时间排序会议 std::sort(meetings.begin(), meetings.end(), compare); std::vector<Meeting> schedule; // 会议安排列表 schedule.push_back(meetings[0]); // 将第一个会议加入安排列表 for (int i = 1; i < meetings.size(); i++) { // 如果当前会议与已安排的最后一个会议不冲突,则将该会议加入安排列表 if (meetings[i].start >= schedule.back().end) { schedule.push_back(meetings[i]); } } return schedule; } int main() { std::vector<Meeting> meetings = {{1, 3}, {2, 4}, {3, 6}, {5, 7}, {8, 9}, {9, 10}}; std::vector<Meeting> schedule = scheduleMeetings(meetings); // 输出会议安排 for (int i = 0; i < schedule.size(); i++) { std::cout << "Meeting " << i+1 << ": " << schedule[i].start << "-" << schedule[i].end << std::endl; } return 0; } ``` 以上代码使用了结构体 `Meeting` 来表示一个会议,其中包含开始时间和结束时间。首先,通过定义一个比较函数 `compare` 来按照会议结束时间进行排序。然后,通过 `scheduleMeetings` 函数来实现会议安排的贪心算法。最后,在 `main` 函数中调用 `scheduleMeetings` 函数并输出会议安排结果。 运行以上代码,会输出以下结果: ``` Meeting 1: 1-3 Meeting 2: 5-7 Meeting 3: 8-9 ``` 这表示在给定的会议列表中,按照贪心算法安排的会议有三个:第一个会议从1到3,第二个会议从5到7,第三个会议从8到9。这些会议之间不存在时间冲突,并且结束时间最早。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

技术宅小温

你小小的鼓励,是我搬砖的动力!

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值