請(qǐng)你來實(shí)現(xiàn)一個(gè) myAtoi(string s) 函數(shù),使其能將字符串轉(zhuǎn)換成一個(gè) 32 位有符號(hào)整數(shù)(類似 C/C++ 中的 atoi 函數(shù))。
函數(shù) myAtoi(string s) 的算法如下:
- 讀入字符串并丟棄無用的前導(dǎo)空格
- 檢查下一個(gè)字符(假設(shè)還未到字符末尾)為正還是負(fù)號(hào)哲泊,讀取該字符(如果有)痰憎。 確定最終結(jié)果是負(fù)數(shù)還是正數(shù)略水。 如果兩者都不存在,則假定結(jié)果為正刹帕。
- 讀入下一個(gè)字符吵血,直到到達(dá)下一個(gè)非數(shù)字字符或到達(dá)輸入的結(jié)尾。字符串的其余部分將被忽略偷溺。
- 將前面步驟讀入的這些數(shù)字轉(zhuǎn)換為整數(shù)(即蹋辅,"123" -> 123, "0032" -> 32)挫掏。如果沒有讀入數(shù)字侦另,則整數(shù)為 0 。必要時(shí)更改符號(hào)(從步驟 2 開始)尉共。
- 如果整數(shù)數(shù)超過 32 位有符號(hào)整數(shù)范圍 [?231, 231 ? 1] 褒傅,需要截?cái)噙@個(gè)整數(shù),使其保持在這個(gè)范圍內(nèi)袄友。具體來說殿托,小于 ?231 的整數(shù)應(yīng)該被固定為 ?231 ,大于 231 ? 1 的整數(shù)應(yīng)該被固定為 231 ? 1 剧蚣。
返回整數(shù)作為最終結(jié)果支竹。
注意:
本題中的空白字符只包括空格字符 ' ' 。
除前導(dǎo)空格或數(shù)字后的其余字符串外鸠按,請(qǐng)勿忽略 任何其他字符
來源:力扣(LeetCode)
鏈接:https://leetcode-cn.com/problems/string-to-integer-atoi
著作權(quán)歸領(lǐng)扣網(wǎng)絡(luò)所有礼搁。商業(yè)轉(zhuǎn)載請(qǐng)聯(lián)系官方授權(quán),非商業(yè)轉(zhuǎn)載請(qǐng)注明出處待诅。
問題分析
需要思考如下幾個(gè)問題叹坦。
輸入有幾種類型?哪一部分是我們需要處理的部分
- 數(shù)字
- 整數(shù)范圍內(nèi)
- 正整數(shù)
- 負(fù)整數(shù)
- 0
- 整數(shù)范圍外
- 小于最小邊界值
- 大于最大邊界值
- 非數(shù)字
- 混合數(shù)組
- 前數(shù)字后子母
- 前字母后數(shù)字
- 中間數(shù)字
- 純字母
根據(jù)題目進(jìn)行分析:
我們需要處理的內(nèi)容有
- 正負(fù)數(shù)和0
檢查下一個(gè)字符(假設(shè)還未到字符末尾)為正還是負(fù)號(hào)卑雁,讀取該字符(如果有)募书。 確定最終結(jié)果是負(fù)數(shù)還是正數(shù)。 如果兩者都不存在测蹲,則假定結(jié)果為正莹捡。
- 混合數(shù)字的前數(shù)字后字母
讀入下一個(gè)字符,直到到達(dá)下一個(gè)非數(shù)字字符或到達(dá)輸入的結(jié)尾扣甲。字符串的其余部分將被忽略篮赢。
- 其他非數(shù)字類型輸出0
將前面步驟讀入的這些數(shù)字轉(zhuǎn)換為整數(shù)(即,"123" -> 123琉挖, "0032" -> 32)启泣。如果沒有讀入數(shù)字,則整數(shù)為 0 示辈。必要時(shí)更改符號(hào)(從步驟 2 開始)
- 整數(shù)范圍之外輸出邊界值
如果整數(shù)數(shù)超過 32 位有符號(hào)整數(shù)范圍 [?231, 231 ? 1] 寥茫,需要截?cái)噙@個(gè)整數(shù),使其保持在這個(gè)范圍內(nèi)矾麻。具體來說纱耻,小于 ?231 的整數(shù)應(yīng)該被固定為 ?231 芭梯,大于 231 ? 1 的整數(shù)應(yīng)該被固定為 231 ? 1 。
綜上我們將其流程總結(jié)為:
那么我們針對(duì)每個(gè)流程進(jìn)行梳理
- 前導(dǎo)空格去除
從前往后遇到第一個(gè)非空格認(rèn)為前導(dǎo)空格去除結(jié)束 - 正負(fù)號(hào)判定
去除空格判定結(jié)束后的下一個(gè)字符是非(-)號(hào)數(shù)字或者字母或者是一個(gè)(-)號(hào) - 數(shù)字字符串提取
從正負(fù)號(hào)判定之后的第一個(gè)字符開始,遇到下一個(gè)非數(shù)字結(jié)束 - 數(shù)字字符串轉(zhuǎn)化
- 在整數(shù)范圍 [?231, 231 ? 1] 內(nèi)輸出當(dāng)前數(shù)字
- 在下邊界之外,輸出下邊界值
- 在上邊界之外弄喘,輸出上邊界值
- 結(jié)果輸出
正常輸出結(jié)果
第四步衍生子問題:
邊界值如何判定是否超綱玖喘?
判定依據(jù):- 長度大于32位
- 從左到右依次判定當(dāng)前值是否小于邊界值轉(zhuǎn)換的字符串
則針對(duì)每一個(gè)小點(diǎn)我們可以寫出代碼
- 前導(dǎo)空格去除
private String replaceBlank(String s){
int i = 0;
for (char c : s.toCharArray()) {
if (c != ' '){
break;
}else {
i++;
}
}
return s.substring(i);
}
- 正負(fù)號(hào)判定
private boolean hasMinus(String c) {
if (c.charAt(0) == '-'){
return true;
}
return false;
}
- 數(shù)字字符串提取
private String extractionOfDigital(String rplString) {
StringBuilder builder = new StringBuilder();
rplString = replaceFirstZero(rplString);
// 去除前面的0
for (char c : rplString.toCharArray()) {
if (c >= '0' && c <= '9'){
builder.append(c);
}else {
break;
}
}
return builder.toString();
}
private String replaceFirstZero(String s){
int i = 0;
for (char c : s.toCharArray()) {
if (c == '0'){
i++;
}else {
break;
}
}
return s.substring(i);
}
- 數(shù)字字符串轉(zhuǎn)化
private Integer convertsAStringToANumber(String numStr, boolean hasMinus) {
if (numStr.equals("")){
return 0;
}
if (numStr.length() > 10){
if (!hasMinus){
return Integer.MAX_VALUE;
}else {
return Integer.MIN_VALUE;
}
}
if (numStr.length() < 10){
if (hasMinus){
return Integer.valueOf("-"+numStr);
}else {
return Integer.valueOf(numStr);
}
}
if (hasMinus){
// 負(fù)數(shù)
String minValue = Integer.MIN_VALUE + "";
int i = 0;
char[] numStrC = ("-"+numStr).toCharArray();
boolean isGreaterThanThe = false;
for (char c : minValue.toCharArray()) {
char n = numStrC[i++];
if (n > c){
isGreaterThanThe = true;
break;
}else if (n < c){
break;
}
}
if (isGreaterThanThe){
return Integer.MIN_VALUE;
}else {
return Integer.valueOf("-"+numStr);
}
}else {
// 正數(shù)
String minValue = Integer.MAX_VALUE + "";
int i = 0;
char[] numStrC = numStr.toCharArray();
boolean isGreaterThanThe = false;
for (char c : minValue.toCharArray()) {
char n = numStrC[i++];
if (n > c){
isGreaterThanThe = true;
break;
}else if (n < c){
break;
}
}
if (isGreaterThanThe){
return Integer.MAX_VALUE;
}else {
return Integer.valueOf(numStr);
}
}
}
整體代碼為:
public class Main {
public static void main(String[] args) {
new Main().test();
}
public void test(){
System.out.println(new Solution().myAtoi("1095502006p8"));
}
class Solution {
public int myAtoi(String s) {
if (s == null || s.equals("")){
return 0;
}
// 前導(dǎo)空格去除
String rplString = replaceBlank(s);
if (rplString.length() == 0){
return 0;
}
boolean hasMinus = hasMinus(rplString);
if (rplString.startsWith("-") ||rplString.startsWith("+")){
rplString = rplString.substring(1);
}
String numStr = extractionOfDigital(rplString);
Integer num = convertsAStringToANumber(numStr,hasMinus);
return num;
}
private Integer convertsAStringToANumber(String numStr, boolean hasMinus) {
if (numStr.equals("")){
return 0;
}
if (numStr.length() > 10){
if (!hasMinus){
return Integer.MAX_VALUE;
}else {
return Integer.MIN_VALUE;
}
}
if (numStr.length() < 10){
if (hasMinus){
return Integer.valueOf("-"+numStr);
}else {
return Integer.valueOf(numStr);
}
}
if (hasMinus){
// 負(fù)數(shù)
String minValue = Integer.MIN_VALUE + "";
int i = 0;
char[] numStrC = ("-"+numStr).toCharArray();
boolean isGreaterThanThe = false;
for (char c : minValue.toCharArray()) {
char n = numStrC[i++];
if (n > c){
isGreaterThanThe = true;
break;
}else if (n < c){
break;
}
}
if (isGreaterThanThe){
return Integer.MIN_VALUE;
}else {
return Integer.valueOf("-"+numStr);
}
}else {
// 正數(shù)
String minValue = Integer.MAX_VALUE + "";
int i = 0;
char[] numStrC = numStr.toCharArray();
boolean isGreaterThanThe = false;
for (char c : minValue.toCharArray()) {
char n = numStrC[i++];
if (n > c){
isGreaterThanThe = true;
break;
}else if (n < c){
break;
}
}
if (isGreaterThanThe){
return Integer.MAX_VALUE;
}else {
return Integer.valueOf(numStr);
}
}
}
private String extractionOfDigital(String rplString) {
StringBuilder builder = new StringBuilder();
rplString = replaceFirstZero(rplString);
// 去除前面的0
for (char c : rplString.toCharArray()) {
if (c >= '0' && c <= '9'){
builder.append(c);
}else {
break;
}
}
return builder.toString();
}
private String replaceFirstZero(String s){
int i = 0;
for (char c : s.toCharArray()) {
if (c == '0'){
i++;
}else {
break;
}
}
return s.substring(i);
}
private boolean hasMinus(String c) {
if (c.charAt(0) == '-'){
return true;
}
return false;
}
private String replaceBlank(String s){
int i = 0;
for (char c : s.toCharArray()) {
if (c != ' '){
break;
}else {
i++;
}
}
return s.substring(i);
}
}
}