(8) String conversion to Integer (ATOI)

Takeaway:

A Description of the topic

Overview of Two Solutions (Mind Mapping)

Three complete solutions

Scheme 1

1) code:

/ / plan 1
var myAtoi = function(s) {
    const l = s.length,
        numStrArr = ['0'.'1'.'2'.'3'.'4'.'5'.'6'.'7'.'8'.'9'];
    
    let index = 0.// Positive and negative cases
        sign = undefined.// The result string
        resStr = ' ';

    // 1) Remove the preceding space character
    while (index < l && s[index] === ' ') {
        index++;
    }
    
    // 2) After the preceding space character, the first character must be a "+", "-" or numeric character
    // Return 0 if not
    if (index < l) {
        if (s[index] === The '-' || s[index] === '+' ) {
            sign = s[index];
            resStr += sign;
        } else {
            if (numStrArr.includes(s[index])) {
                resStr += s[index];
            } else {
                return 0; }}}// 3) After the + and - signs are determined, the numeric characters are read continuously (if the non-numeric characters are encountered, there is no need to read further) and stored continuously in resStr
    index += 1;
    while (index < l && numStrArr.includes(s[index])) {
        resStr += s[index];
        index++;
    }

    let resValue = parseInt(resStr);
    // Boundary 1: "+-12" (core: only +, - characters, etc., when parseInt(resStr) is NaN, that is, Not A Number)
    resValue = Number.isNaN(resValue) ? 0 : resValue;
    // Boundary 2: handle the upper and lower bounds of the scope
    resValue = resValue < Math.pow(-2.31)?Math.pow(-2.31) : resValue;
    resValue = resValue > Math.pow(2.31) - 1 ? Math.pow(2.31) - 1 : resValue;

    // 4) Return the final result
    return resValue;
}
Copy the code

Scheme 2

1) code:

// Select parseInt() from JS; // Select parseInt() from JS;
var myAtoi = function(str) {
    // 1) use parseInt() directly, which saves a lot of "preprocessing".
    let resValue = parseInt(str);

    // 2) Boundary processing
    // Boundary 1: "+-12" (core: only +, - characters, etc., when parseInt(resStr) is NaN, that is, Not A Number)
    if (isNaN(resValue)) {
        return 0;
    } else {
        // Boundary 2: handle the upper and lower bounds of the scope
        resValue = resValue < Math.pow(-2.31)?Math.pow(-2.31) : resValue;
        resValue = resValue > Math.pow(2.31) - 1 ? Math.pow(2.31) - 1 : resValue;
    }

    // 3) Return the final result
    return resValue;
};
Copy the code

3 solution 3

1) code:

// Solution 3 state machine
var myAtoi = function(str) {
    // Select * from char; // Select * from char
    const getStateIndex = char= > {
        const numStrArr = ['0'.'1'.'2'.'3'.'4'.'5'.'6'.'7'.'8'.'9'];
        // Initialize the flow to an 'end' state
        let resStateIndex = 3;

        if (char === ' ') {
            resStateIndex = 0;
        } else if (char === '+' || char === The '-') {
            resStateIndex = 1;
        } else if (numStrArr.includes(char)){
            resStateIndex = 2;
        }

        return resStateIndex;
    };

    // 1) initialize various values, especially tableMap definition!!
    const l = str.length,
        // Tabular form of the state machine
        tableMap = {
            'start': ['start'.'signed'.'in_number'.'end'].'signed': ['end'.'end'.'in_number'.'end'].'in_number': ['end'.'end'.'in_number'.'end'].'end': ['end'.'end'.'end'.'end']};// state: indicates the current state value
    let state = 'start',
        sign = 1,
        index = 0,
        resValue = 0;

    // 2) Iterate over the string STR and update the values of state, resValue and sign according to the current character char.
    / / when the index > = l | | state = = = 'end', exit the traversal
    while (index < l) {
        const char = str[index];
        state = tableMap[state][getStateIndex(char)];
        if (state == 'in_number') {
            resValue = resValue * 10 + parseInt(char);
        } else if (state === 'signed') {
            // Since sign is initialized to 1, it is necessary to handle it if it is '-'
            if (char === The '-') {
                sign = -1;
            }
        }
        
        index++;
        // Optimize: if the current state is 'end', you can exit without traversing again
        if (state === 'end') {
            break; }}// 3) Restore the symbol
    resValue *= sign;

    // 4) Boundary processing
    // Boundary 1: handle the upper and lower bounds of the scope
    resValue = resValue < Math.pow(-2.31)?Math.pow(-2.31) : resValue;
    resValue = resValue > Math.pow(2.31) - 1 ? Math.pow(2.31) - 1 : resValue;

    // 5) Return the result
    return resValue;
}
Copy the code