请你来实现一个 atoi 函数,使其能将字符串转换成整数。
首先,该函数会根据需要丢弃无用的开头空格字符,直到寻找到第一个非空格的字符为止。接下来的转化规则如下:
如果第一个非空字符为正或者负号时,则将该符号与之后面尽可能多的连续数字字符组合起来,形成一个有符号整数。 假如第一个非空字符是数字,则直接将其与之后连续的数字字符组合起来,形成一个整数。 该字符串在有效的整数部分之后也可能会存在多余的字符,那么这些字符可以被忽略,它们对函数不应该造成影响。 注意:假如该字符串中的第一个非空格字符不是一个有效整数字符、字符串为空或字符串仅包含空白字符时,则你的函数不需要进行转换,即无法进行有效转换。
在任何情况下,若函数不能进行有效的转换时,请返回 0 。
正常遍历
#include<iostream>
#include <cmath>
#include<vector>
#include<algorithm>
class Solution {
public:
int myAtoi(string str) {
//利用long long类型保证可以越界比较
long long result = 0;
//i是记录位置
int i = 0;
//flag是记录正负号
int flag = 1;
//遇到空格先跳过
while (i < str.size() && str[i] == ' ') {
i++;
}
if (str[i] == '-') {
flag = -1;
i++;
}
else if (str[i] == '+') {
i++;
}
//第一个字符是非数字字符,不需要转换,返回0
if (str[i]<'0' || str[i]>'9') {
return 0;
}
while (i < str.size() && ('0' <= str[i] && str[i] <= '9')) {
//累加求数
result = result * 10 + (str[i] - '0');
//去掉符号的结果溢出,跳出循环
if (result >= INT_MAX)
{
break;
}
i++;
}
result = result * flag;
//判断是否溢出
if (result >= INT_MAX) {
return INT_MAX;
}
if (result <= INT_MIN) {
return INT_MIN;
}
return result;
}
};
有限状态机
- 状态转移表
| ' ' | +/- | 数字 | 其他 | |
|---|---|---|---|---|
| start | start | signed | in_number | end |
| signed | end | end | in_number | end |
| in_number | end | end | in_number | end |
| end | end | end | end | end |
#include<iostream>
#include <cmath>
#include<vector>
#include<algorithm>
#include <unordered_map>
using namespace std;
class StateMachine {
private:
//起始状态
string state = "start";
//map映射,方便做状态转换
unordered_map<string, vector<string>>stateTable = {
{"start",{"start","signed","inNum","end"}},
{"signed",{"end","end","inNum","end"}},
{"inNum",{"end","end","inNum","end"}},
{"end",{"end","end","end","end"}}
};
//根据传入的字符返回状态
int getState(char c) {
if (c == ' ') {
return 0;
}
if (c == '+' || c == '-') {
return 1;
}
if (isdigit(c)) {
return 2;
}
return 3;
}
public:
//一定要初始化result和flag
long long result=0;
int flag=1;
void getResult(char c) {
state = stateTable[state][getState(c)];
//是数字,进行求和运算和判断溢出
if (state =="inNum") {
result = result * 10 + (c - '0');
//注意此时result为正数或者0
result = (flag == 1 ? min((long long)INT_MAX, result) : min(-(long long)INT_MIN, result));
}
//开始状态下遇到正负号
else if (state == "signed") {
if (c == '-') {
flag = -1;
}
}
}
};
class Solution {
public:
StateMachine stateMachine;
int myAtoi(string str) {
for (char c : str) {
stateMachine.getResult(c);
}
return stateMachine.result*stateMachine.flag;
}
};