Adding a Coding Challenge
This tutorial will explain how you can create a Coding Challenge. Let's pick a simple problem: given a string, you want the user to write a program that return its first character. So, for example, if abcd is input to the program, the program must return a.
The only way to automatically evaluate if a submitted piece of code is correct is to see if it works for a variety of inputs. For example, we can input xyz, 123 and op, the program must return x, 1 and o as output. These inputs that are used to check the validity of a program are called Test Cases. So, the main components of a Coding Challenge are:
- A Problem Statement, preferably written in Markdown
- A list of Test Cases
- An editor (IDE) where the user writes the program that takes in the input and returns an output
The video below shows Socratease's interface for exactly this problem
Reading user input (Standard Input) is notoriously hard, especially if one is reading inputs spanning multiple lines. So, most programming platforms, including ours, set up some code that does this reading of input. This lets the user focus on the core logic, and not worry about input/output. For instance, in the video above, you can see that the user doesn't have to do any input/output. They just have to fill a function. In other products, this is called Driver Code. We call it Boilerplate. There are two types of Boilerplates:
- User Boilerplate: Whatever a candidate sees on the IDE. This typically has the function name and scope and the user must write the logic within it. Whatever the IDE loads with (as seen in the video above) is the User Boilerplate.
- Compiler Boilerplate: Code not shown to the user, which takes user input, parses it & then calls the User Boilerplate function.
Standard Input is always a String. The Compiler Boilerplate's role is to convert the string into a datatype that the User Boilerplate can consume. For example, if the question is to find the largest integer in a list, the input will be a string like 10 23 2 4. The Compiler Boilerplate will convert this into a list [10, 23, 2, 4] Different languages will obviously need different code to achieve this. So, User and Compiler Boilerplates are specific to the problem being solved, and the programming language.
Let's continue with our example of extracting the first character of a given string. Below, you can see the full code that is stored on Socratease. We are showing the Compiler Boilerplate as well, though the user will not see it in the IDE.
You can clearly see that the Compiler Boilerplate is doing the input and output work. For example, in JS, the readline() function is reading the string as an input. It then calls the extractFirstChar() function and prints to standard output. The user needn't concern herself with all this. They just need to write the login within the definition of the extractFirstChar() function.
The image below shows how you would enter the Compiler and User Boilerplate when you are creating a Coding Challenge. This Github URL has sample code for reading single lines as strings for other languages.
To execute an array function, accept a space-separated string (for example 4 5 6 7) as input. You can then split the string and convert it into an array. What goes into Compiler Boilerplate and what goes into User Boilerplate isn't clearly defined. The more code in Compiler Boilerplate, the easier it is for the user as they can focus purely on the logic.
As mentioned earlier, test cases are used to verify if the submitted code is valid or not. There are two types of test cases:
- Sample Test Case: Shown to the user so that they can verify if their code is working or not, before they submit. Typically, around 3 sample test cases are added to a problem.
- Real Test Case: These test cases are hidden from the user (otherwise, the user can write code that returns exactly the output that is expected). There can be 5-10 real test cases and they are checked when the user finally submits the code. The points scored by a user are pro-rated based on how many real test cases pass.
You can see real and sample test cases in the image above.
More complex problems need multiple parameters. It is easiest to split the multiple parameters on different lines. For example, suppose you the problem is to find an element in an array, given its index. The input can then be across three lines:
5 6 3 2
Here, 4 in the first line refers to the number of elements in the array. 5 6 3 2 in the next line refers to the zero-indexed array [5, 6, 3, 2] and 3 in the last line denotes the index of which we want the value. Obviously, the answer here is 2. Below, you can see how the compiler boilerplate is converting the 3 lines into structured data index and arr
This Github URL has sample code for reading multiple lines as strings for other languages.
On creating a new Coding Challenge, you'll see an input field as shown below. If you have the question in a specific format on a public github repo, you can import it directly from there, instead of filling out all the fields.
This Github URL has a sample question. You can use a different Github URL, of course. Once you paste this URL into the input field and click on the Fetch button, the question-related fields get auto-populated. You can see this in action in the gif below.