Program 4: loops

Programming the Web: An Introduction (Spring 2021)

Due date (revised): Tuesday, March 9 at 5pm EST


General instructions


The problems themselves

  1. Complete the function sumSkipRange(start, stop, skip) so that it returns the sum of the sequence of integers that runs from start up to, but not including stop, such that the difference between consecutive numbers in the sequence is skip. You can assume that the input values are all integers and that skip is positive. Examples:

    > sumSkipRange(1, 10, 1)     // 1 + 2 + 3 + ... + 9
      45
    > sumSkipRange(20, 50, 10)   // 20 + 30 + 40
      90
    > sumSkipRange(5, 30, 7)     // 5 + 12 + 19 + 26
      62
    > sumSkipRange(10, 5, 2)     // 0 because 10 is already >= 5
      0
  2. Complete doubleString(s) so that it returns a version of string s where each character is repeated twice as in:

    > doubleString('')
      ""
    > doubleString('Very exciting!')
      "VVeerryy  eexxcciittiinngg!!"
  3. Complete oddCount(n) so that it returns the number of odd numbers larger than 1 and less than n that are neither divisible by 3 nor 7. Examples:

    > oddCount(10)    // 5
      1
    > oddCount(20)    // 5, 11, 13, 17, 19
      5
    > oddCount(40)    // 5, 11, 13, 17, 19, 23, 25, 29, 31, 37 
      10
  4. Complete codeStreak(startChar, n) so that it returns a string of n characters, beginning with startChar such that the ASCII/Unicode values corresponding to each character increases by one with each successive character. For example, since the character A corresponds to code 65, codeStreak(A, 3) would generate the string ABC. Make use of the .charCodeAt method and the String.fromCharCode function. Other examples:

    > codeStreak('whatever', 0)
      ""
    > codeStreak('b', 5)
      "bcdef"
    > codeStreak('0', 10)
      "0123456789"
  5. Complete removeNonletters(s) so that it returns a filtered version of s consisting only of its alphabetic characters. Examples:

    > removeNonletters('LeaveItAsIs')
      "LeaveItAsIs"
    > removeNonletters('')
      ""
    > removeNonletters('!@#$%^&*()1234567890')
      ""
    > removeNonletters('**Wow that is cool!**')
      "Wowthatiscool"
  6. Complete triangleString(s) so that it returns a multiline string (i.e., a string with newline symbols in it) such that each character of s is repeated an increasing number of times according to its position in the string and such that each group, appears on its own line. Use nested loops. Examples:

    > triangleString('')
      ""
    > triangleString('A')
      "A\n"
    > console.log(triangleString('ABC'));
      A
      BB
      CCC
  7. Complete separate(s, separator) so that it returns a version of string s such that string separator appears between each character in s. Examples:

    > separate('','!!!')   // nothing to separate
      ""
    > separate('a','!!!')  // still nothing to separate
      "a"
    > separate('abc',',')
      "a,b,c"
  8. Complete parensMatched(s) so that it returns true if the parentheses that occur in string s (if any) occur in a “matched” way, meaning, there are the same number of left (() parentheses as right ()) parentheses and that reading from left-to-right, every right parenthesis has a corresponding left one that occurs before it in the string. Examples:

    > parensMatched('')
      true
    > parensMatched('nothing to see here')
      true
    > parensMatched('((a+b)*(c+d))')
      true
    > parensMatched(')this is bogus(')
      false
    > parensMatched, '(((open))')
      false
  9. Complete inOrder(s) so that it returns true if the characters in s occur in lexicographic (alphabetical) order. Examples:

    > inOrder('')
      true
    > inOrder('z')
      true
    > inOrder('ghost')
      true
    > inOrder('!39Ga}')   // ASCII codes for those symbols are increasing order
      true
    > inOrder('gHost')    // case sensitive!
      false
    > inOrder('A+')
      false
  10. Complete the strangely named function malignRust(s) so that it returns a new string according to the following rules: if the length of the string under consideration is less than 2, it returns the string it has built up so far; otherwise it glues the first character of the string onto the end of the new string it is building. If the length of the string is an even number, it repeats the process but only considering the first half of the string, and if the length is odd, it repeats the process but using the first character of the string with three whole copies of the string concatenated after it. This is best illustrated with a detailed example. Suppose its input is 'abcde':

    string being processed     string being built      notes
    ----------------------------------------------------------------------
    'abcde'                      ''                    odd, larger than 1
    'aabcdeabcdeabcde'           'a'                   even, larger than 1
    'aabcdeab'                   'aa'                  even, larger than 1
    'aabc'                       'aaa'                 even, larger than 1
    'aa'                         'aaaa'                even, larger than 1
    'a'                          'aaaaa'               stop
    
    returns 'aaaaa'

    Along with your code, include a comment that indicates whether the loop you use to solve the problem is definite or indefinite and explain why.

    For this problem you are welcome to use JavaScript’s .slice method.

    Bonus: include a comment explaining why the function is called malignRust.


Remember, all of the functions should be pure: they take one or more arguments and return a value. Make sure that your functions have a single return statement as the last statement within the body of the function. Keep the return simple: just return a variable. Use variable assignments to compute your result. Each function should have at least one let assignment.

Your code should not use alert, prompt, or confirm.

With numbers, you can use the standard five arithmetic operations:

+   -   *   /   %

and the six arithmetic comparison operations:

===   !==   <   >   <=   >=

You may also use Math.floor(...) and Math.random().

With Boolean values you can use the literals true and false and the three standard Boolean operators:

!   &&   ||

With strings, you can use:

===   !==   <    >   <=   >=   .length
.toLowerCase()   .toUpperCase()   .charCodeAt()    String.fromCharCode()

and you can access individual characters within the string by using [] notation.


To experiment more directly with my solution, you can open up on a console while viewing this page and try examples such as:

> sumSkipRange(20, 50, 10)
  90
> doubleString('Help!')
  "HHeellpp!!"
> oddCount(20)
  5
> codeStreak('b', 5)
  "bcdef"
> removeNonletters('**Wow that is cool!**')
  "Wowthatiscool"
> console.log(triangleString('ABCD'));
  A
  BB
  CCC
  DDDD
> separate('abc',',')
  "a,b,c"
> parensMatched('((a+b)*(c+d))')
  true
> inOrder('ghost')
  true
> malignRust('abcdef')
  "aaaaaaaa"