剑指 Offer(第2版)面试题 20:表示数值的字符串

剑指 Offer(第2版)面试题 20:表示数值的字符串

  • 剑指 Offer(第2版)面试题 20:表示数值的字符串
    • 解法1:模拟
    • 解法2:分段匹配
    • 解法 3:DFA

剑指 Offer(第2版)面试题 20:表示数值的字符串

题目来源:31. 表示数值的字符串

解法1:模拟

注意以下几点:

  1. 小数可以没有整数部分,例如.123等于0.123;
  2. 小数点后面可以没有数字,例如233.等于233.0;
  3. 小数点前面和后面可以有数字,例如233.666;
  4. 当e或E前面没有数字时,整个字符串不能表示数字,例如.e1、e1;
  5. 当e或E后面没有整数时,整个字符串不能表示数字,例如12e、12e+5.4。

可能存在字符串前后有空格的情况,下面的函数可以删除空格:

string delSpaceStr(string s)
{int n = s.length(), i = 0, j = n - 1;while (i < n && s[i] == ' ')i++;while (j >= 0 && s[j] == ' ')j--;if (i <= j)return s.substr(i, j - i + 1);return "";
}

代码:

class Solution
{
public:bool isNumber(string s){if (s[0] == '-' || s[0] == '+')s = s.substr(1);if (s.empty() || s[0] == '.' && s.size() == 1)return false;int n = s.length();int point = 0, e = 0;for (int i = 0; i < n; i++){if (isdigit(s[i])){// 如果 s[i] 是数字 '0'~'9',跳过continue;}else if (s[i] == '.') // 如果 s[i] 是小数点{point++;if (e || point > 1) {// 小数点不能超过 1 个,且小数点不能出现在 'e'/'E' 之后return false;}}else if (s[i] == 'e' || s[i] == 'E'){e++;if (e > 1){return false;}if (i == 0 || i == n - 1){// 'e'/'E' 不能出现在数值的开头和末尾return false;}if (i == 1 && s[0] == '.'){// 不能有 '.e' 或 '.E'return false;}if (s[i + 1] == '+' || s[i + 1] == '-'){// 'e'/'E' 后可以接加减号,但是加减号不能是末尾if (i + 2 == n)return false;// 跳过加减号i++;}}else{// 其他字符都是非法的!return false;}}return true;}
};

复杂度分析:

时间复杂度:O(n),其中 n 是字符串 s 的长度。

空间复杂度:O(1)。

解法2:分段匹配

官方解法。

表示数值的字符串遵循模式 A[.[B]][E|eC] 或者 .[B][E|eC],其中 A 是数值的整数部分,B 紧跟小数点,是数值的小数部分,C紧跟着 ‘e’/‘E’,是数值的指数部分。

在数值里可能没有数值的整数部分,因此 A 是可有可无的。如果一个数没有整数部分,那么它必须有小数部分。

另外,A 和 C 都可能以 ‘+’/‘-’ 开头,B 一定不能以 ‘+’/‘-’ 开头。

代码:

class Solution
{
public:bool isNumber(string s){if (s.empty())return false;int idx = 0;// 扫描数值的整数部分bool numeric = scanInteger(s, idx);// 如果出现了 '.',则接下来是数值的小数部分if (s[idx] == '.'){idx++;numeric = scanUnsignedInteger(s, idx) || numeric;}// 如果出现了 'e'/'E',则接下来是数值的指数部分if (s[idx] == 'e' || s[idx] == 'E'){idx++;numeric = scanInteger(s, idx) && numeric;}return numeric && idx == s.length();}bool scanInteger(const string s, int &index){if (s[index] == '+' || s[index] == '-')index++;return scanUnsignedInteger(s, index);}bool scanUnsignedInteger(const string s, int &index){int begin = index;while (index < s.length() && isdigit(s[index]))index++;return index > begin;}
};

复杂度分析:

时间复杂度:O(n),其中 n 是字符串 s 的长度。

空间复杂度:O(1)。

解法 3:DFA

看不懂的炫技解法,和状态机有关。

class Solution {
public:bool isNumber(string s) {if(s.empty()) return false;int n = s.size();int state = 0;vector<bool> finals({0, 0, 0, 1, 0, 1, 1, 0, 1}); // 合法的终止状态vector<vector<int> > transfer({{0,  1,  6,  2,  -1, -1},{-1, -1, 6,  2,  -1, -1},{-1, -1, 3,  -1, -1, -1},{8,  -1, 3,  -1, 4,  -1},{-1, 7,  5,  -1, -1, -1},{8,  -1, 5,  -1, -1, -1},{8,  -1, 6,  3,  4,  -1},{-1, -1, 5,  -1, -1, -1},{8,  -1, -1, -1, -1, -1},});for(int i = 0; i < n; ++i) {state = transfer[state][_make(s[i])];if(state < 0) return false;}return finals[state];}private:int _make(const char& c) {switch(c) {case ' ': return 0;case '+': return 1;case '-': return 1;case '.': return 3;case 'e': return 4;case 'E': return 4;default: return _number(c);}}int _number(const char& c) {if(c >= '0' && c <= '9') return 2;else return 5;}
};

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/206260.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

linux进程通信

匿名管道 struct_file的两套资源 管道只能单向通信 特征 1.如果管道没有数据 读端在读 默认会直接阻塞正在读取的进程 2.写端写满 在写会阻塞 等待对方读取 管道设计 命名管道 实现管道通信 #pragma once #include<iostream> #include<string> #include<sys/…

windows MYSQL解决中文乱码问题

1.首先确保你已经把mysql配置了环境变量 2.打开window终端 3.输入mysql -u root -p 4.输入密码&#xff0c;就是安装的时候设置的root超级管理员权限密码 5.输入&#xff1a; SHOW VARIABLES LIKE ‘character%’; 出现上图&#xff0c;说明就会出现中文乱码问题。 6.该怎么办…

前端中的响应式布局与各个端适配

什么是响应式布局&#xff1f; 响应式布局指的是同一页面在不同屏幕尺寸下有不同的布局。在移动互联网高度发达的今天&#xff0c;我们在桌面浏览器上开发的网页已经无法满足在移动设备上查看的需求。传统的开发方式是PC端开发一套页面&#xff0c;手机端再开发一套页面。但是…

使用python脚本一个简单的搭建ansible集群

1.环境说明&#xff1a; 角色主机名ip地址控制主机server192.168.174.150受控主机/被管节点client1192.168.174.151受控主机/被管节点client2192.168.174.152 2.安装python和pip包 yum install -y epel-release yum install -y python python-pip 3.pip安装依赖库 pip in…

redis-学习笔记(hash)

Redis 自身已经是 键值对 结构了 Redis 自身的键值对就是通过 哈希 的方式来组织的 把 key 这一层组织完成后, 到了 value 这一层, 还可以用 哈希类型 来组织 (简单的说就是哈希里面套哈希 [数组里面套数组 -> 二维数组] ) [ field value ] hset key field value [ field va…

【Spring】Spring 微服务中的数据分区和分片

文章目录 前言数据分区简介分区的本质分区类型为什么分区很重要&#xff1f;分片简介了解分片分片的机制为什么选择分片&#xff1f;在 Spring 微服务中实现分区和分片用于分区的 Spring Data JPA挑战与最佳实践分区和分片时的注意事项选择正确的键重新分片和重新分区基础设施和…

【Java 基础】23 国际化

文章目录 1.概念2.原理1&#xff09;Locale2&#xff09;ResourceBundle3&#xff09;MessageFormat 3.例子1&#xff09;准备资源文件2&#xff09;加载资源文件3&#xff09;格式化消息&#xff08;非必须&#xff09; 总结 在全球化的今天&#xff0c;开发支持多语言的应用变…

STM32F1的TIM输出比较(PWM)

目录 1. OC&#xff08;Output Compare&#xff09;输出比较 2. PWM简介 3. 输出比较通道(高级) 4. 输出比较通道(通用) 5. PWM基本结构 6. 配置介绍 6.1 输出比较模块配置 6.2 给输出比较结构体赋一个默认值 6.3 配置强制输出模式 6.4 配置CRR寄存器的预装…

【文件上传系列】No.1 大文件分片、进度图展示(原生前端 + Node 后端 Koa)

分片&#xff08;500MB&#xff09;进度效果展示 效果展示&#xff0c;一个分片是 500MB 的 分片&#xff08;10MB&#xff09;进度效果展示 大文件分片上传效果展示 前端 思路 前端的思路&#xff1a;将大文件切分成多个小文件&#xff0c;然后并发给后端。 页面构建 先在页…

低代码与MES:智能制造的新篇章

一、引言 随着工业4.0和智能制造的兴起&#xff0c;企业对于生产过程的数字化、智能化需求日益迫切。制造执行系统&#xff08;MES&#xff09;作为连接计划层与控制层的关键信息系统&#xff0c;在提升生产效率、优化资源配置、保障产品质量等方面发挥着重要作用。然而&#…

AIGC实战——WGAN(Wasserstein GAN)

AIGC实战——WGAN 0. 前言1. WGAN-GP1.1 Wasserstein 损失1.2 Lipschitz 约束1.3 强制 Lipschitz 约束1.4 梯度惩罚损失1.5 训练 WGAN-GP 2. GAN 与 WGAN-GP 的关键区别3. WGAN-GP 模型分析小结系列链接 0. 前言 原始的生成对抗网络 (Generative Adversarial Network, GAN) 在…

深入探索C语言中的二叉树:数据结构之旅

引言 在计算机科学领域&#xff0c;数据结构是基础中的基础。在众多数据结构中&#xff0c;二叉树因其在各种操作中的高效性而脱颖而出。二叉树是一种特殊的树形结构&#xff0c;每个节点最多有两个子节点&#xff1a;左子节点和右子节点。这种结构使得搜索、插入、删除等操作…

【React Hooks】useReducer()

useReducer 的三个参数是可选的&#xff0c;默认就是initialState&#xff0c;如果在调用的时候传递第三个参数那么他就会改变为你传递的参数&#xff0c;实际开发不建议这样写。会增加代码的不可读性。 使用方法&#xff1a; 必须将 useReducer 的第一个参数&#xff08;函数…

MySQL - 并发控制与事务的隔离级别

目录 第1关&#xff1a;并发控制与事务的隔离级别 第2关&#xff1a;读脏 第3关&#xff1a;不可重复读 第4关&#xff1a;幻读 第5关&#xff1a;主动加锁保证可重复读 第6关&#xff1a;可串行化 第1关&#xff1a;并发控制与事务的隔离级别 任务描述 本关任务&#…

JS/jQuery 获取 HTTPRequest 请求标头?

场景&#xff1a;在jquery封装的ajax请求中&#xff0c;默认是异步请求。 需要定一个秘钥进行解密&#xff0c;所以只能存放在请求头中。然后需要值的时候去请求头中读取。 注意&#xff1a;dataType设置&#xff0c;根据请求参数的格式设置&#xff0c;如果是加密字符串&…

(C#)使用sharpcompress压缩解压文件(.rar,.zip,tar.bz2,.7z,.tar.gz)

sharpcompress安装方法 使用Nuget搜索sharpcompress,点击安装即可 1、.rar文件解压代码(不支持rar压缩) using (Stream stream File.OpenRead("C:\Code\sharpcompress.rar")) {var reader ReaderFactory.Open(stream);while (reader.MoveToNextEntry()){if (!re…

linux初级学习

(420条消息) 红帽认证-RHCSA_rhcsa红帽认证_yyyzf的博客-CSDN博客 OS&#xff1a;用户和机器的接口&#xff0c;UI:CMD,GUI shell: 通用格式 命令 选项&#xff08;调控功能&#xff09; 参数&#xff08;操作对象&#xff09;参数 省略参数对象一般使用当前目录作为参数对…

WordPress禁止显示指定类别的文章

使用wordpress禁止输出指定类别的文章可以给get_posts()函数传个数组参数&#xff0c;如下&#xff1a; <div class"widget" id"diary1"> <h3>随机呈现</h3> <ul> <?php $argsarray( numberposts>16, category>-9,-12, …

vue3日常知识点学习归纳

1&#xff0c;父子组件传递&#xff1a; 父组件传递参数 <template><div><!-- 子组件 参数&#xff1a;num 、nums --><child :num"nums.num" :doubleNum"nums.doubleNum" increase"handleIncrease"></child>&l…

JAVA全栈开发 day19_JDBC

一、JDBC 1.JDBC概述 1.1什么是jdbc Java DataBase Connectivity是一种用于执行SQL语句的Java API&#xff0c;它由一组用Java语言编写的类和接口组成。通过这些类和接口&#xff0c;JDBC把SQL语句发送给不同类型的数据库进行处理并接收处理结果。 1.2jdbc的作用 提供java…