Academic Integrity: tutoring, explanations, and feedback — we don’t complete graded work or submit on a student’s behalf.

This is Ocaml or function language Q1. Use pattern matching to write a function

ID: 3834342 • Letter: T

Question

This is Ocaml or function language

Q1. Use pattern matching to write a function called power which takes as parameters the numbers x and n and computes the value of x raised to the power n.

Run your code and demonstrate its results. Include the output in your answer.

Does your function handle negative numbers? Test it. Describe what happens and then provide an explanation for the reason for the results. Include the output in your answer.

Q2. Write a function called is member which take as parameters an item and a list. It returns true if the item exists with the list and false otherwise.

Run your code and demonstrate its results. Include the output in your answer. Which types of lists did you test?

Assignment Submission Instructions

Submit your work as two files:

A .ml or .caml code file (which must execute without warnings or errors)

A Microsoft Word document containing the contents of your code file (see further instructions below

Name your files as follows: YourFirstName_YourLastName_E3 (.ml or .caml, and .doc or .doctx)

In your code file, put your name, assignment name, and the date the assignment work must be submitted, at the top.

The questions and your explanations/reasoning must be included as comments in your code listing. The comments must:

Respond to any questions asked within the primary questions given above

Explain the functioning of the code segments you have written

Provide your reasoning for why you chose to write the code the way you did and if you considered any alternate ways of writing it

Make sure that the file is easily read i.e. it is nicely formatted with blank lines separating code segments, and comments appropriately associated with the relevant code segments, so that one can easily understand what you have written.

Copy your entire code listing and paste it into a Microsoft Word document. In the Microsoft Word document, change the comments text to green-colored font (your code text should be in black-colored font; this Word document too should be easily readable). See example below:

(* Comments here *)

Code statements here

Explanation / Answer

1. Ocaml

OCaml is a general purpose programming language with an emphasis on expressiveness and safety. Developed for more than 20 years at Inria by a group of leading researchers, it has an advanced type system that helps catch your mistakes without getting in your way. It's used in environments where a single mistake can cost millions and speed matters, is supported by an active community, and has a rich set of libraries and development tools.
For all its power, OCaml is also pretty simple, which is one reason it's often used as a teaching language.

Functions

OCaml is a functional programming language: there is no restriction on the definition and use of functions. In other words, functions are ordinary values: a function can be passed as an argument to a function or returned by a function.

Data Types

OCaml offers numerous built-in data types, including:

basic types: integers, floating point numbers, booleans, characters, strings.
more sophisticated data types: tuples, arrays, lists, sets, hash tables, queues, stacks, data streams.

Beyond these powerful built-in types, OCaml offers powerful means of defining new data types: records, enumerations, and sum types. Sum types are a simple and powerful generalization of enumerations. They allow bringing heterogeneous values together into a common type, thanks to the use of tags known as data constructors.

The types defined within a module can be made visible to the module's clients either concretely or abstractly, as the programmer desires. When a type is exported in a concrete manner, its full definition remains known: so, clients of the modules can build or examine values of this type. On the other hand, when a type is exported in an abstract manner, only its name is known outside the module. It then becomes impossible, from the outside, to create or inspect values of this type.

This mechanism provides fine-grained control over data encapsulation, which is mandatory for programming in the large.

Code

#include<stdio.h>

/* Function to calculate x raised to the power y */

int power(int x, unsigned int y)

{

    if (y == 0)

        return 1;

    else if (y%2 == 0)

        return power(x, y/2)*power(x, y/2);

    else

        return x*power(x, y/2)*power(x, y/2);

}

/* Program to test function power */

int main()

{

    int x = 2;

    unsigned int y = 3;

    printf("%d", power(x, y));

    return 0;

}

Time Complexity: O(n)
Space Complexity: O(1)
Algorithmic Paradigm: Divide and conquer.

Above function can be optimized to O(logn) by calculating power(x, y/2) only once and storing it.

/* Function to calculate x raised to the power y in O(logn)*/

int power(int x, unsigned int y)

{

    int temp;

    if( y == 0)

        return 1;

    temp = power(x, y/2);

    if (y%2 == 0)

        return temp*temp;

    else

        return x*temp*temp;

}

Run on IDE

Time Complexity of optimized solution: O(logn)
Let us extend the pow function to work for negative y and float x.

/* Extended version of power function that can work

for float x and negative y*/

#include<stdio.h>

float power(float x, int y)

{

    float temp;

    if( y == 0)

       return 1;

    temp = power(x, y/2);      

    if (y%2 == 0)

        return temp*temp;

    else

    {

        if(y > 0)

            return x*temp*temp;

        else

            return (temp*temp)/x;

    }

}

/* Program to test function power */

int main()

{

    float x = 2;

    int y = -3;

    printf("%f", power(x, y));

    return 0;

}

The program above takes two integers from the user (a base number and an exponent) and calculates the power.

For example: In case of 23

2.

Time complexity of above method is O(n), but it requires O(n) extra space. Following methods solve this with constant extra space.


METHOD (By reversing the list)
This method takes O(n) time and O(1) extra space.
1) Get the middle of the linked list.
2) Reverse the second half of the linked list.
3) Check if the first half and second half are identical.
4) Construct the original linked list by reversing the second half again and attaching it back to the first half

To divide the list in two halves, method of this post is used.
When number of nodes are even, the first and second half contain exactly half nodes. The challenging thing in this method is to handle the case when number of nodes are odd. We don’t want the middle node as part of any of the lists as we are going to compare them for equality. For odd case, we use a separate variable ‘midnode’.

Code

#include<stdio.h>

#include<stdlib.h>

#include<stdbool.h>

/* Link list node */

struct node

{

    char data;

    struct node* next;

};

void reverse(struct node**);

bool compareLists(struct node*, struct node *);

/* Function to check if given linked list is

  palindrome or not */

bool isPalindrome(struct node *head)

{

    struct node *slow_ptr = head, *fast_ptr = head;

    struct node *second_half, *prev_of_slow_ptr = head;

    struct node *midnode = NULL; // To handle odd size list

    bool res = true; // initialize result

    if (head!=NULL && head->next!=NULL)

    {

        /* Get the middle of the list. Move slow_ptr by 1

          and fast_ptrr by 2, slow_ptr will have the middle

          node */

        while (fast_ptr != NULL && fast_ptr->next != NULL)

        {

            fast_ptr = fast_ptr->next->next;

            /*We need previous of the slow_ptr for

             linked lists with odd elements */

            prev_of_slow_ptr = slow_ptr;

            slow_ptr = slow_ptr->next;

        }

        /* fast_ptr would become NULL when there are even elements in list.

           And not NULL for odd elements. We need to skip the middle node

           for odd case and store it somewhere so that we can restore the

           original list*/

if (fast_ptr != NULL)

        {

            midnode = slow_ptr;

            slow_ptr = slow_ptr->next;

        }

        // Now reverse the second half and compare it with first half

        second_half = slow_ptr;

        prev_of_slow_ptr->next = NULL; // NULL terminate first half

        reverse(&second_half); // Reverse the second half

        res = compareLists(head, second_half); // compare

        /* Construct the original list back */

         reverse(&second_half); // Reverse the second half again

          // If there was a mid node (odd size case) which                                                        

         // was not part of either first half or second half.

         if (midnode != NULL)

         {

            prev_of_slow_ptr->next = midnode;

            midnode->next = second_half;

         }

         else prev_of_slow_ptr->next = second_half;

    }

    return res;

}

/*Function to show the reverse method of link list*/

/* Function to reverse the linked list Note that this

    function may change the head */

void reverse(struct node** head_ref)

{

    struct node* prev   = NULL;

    struct node* current = *head_ref;

    struct node* next;

    while (current != NULL)

    {

        next = current->next;

        current->next = prev;

        prev = current;

        current = next;

    }

    *head_ref = prev;

}

/* Function to check if two input lists have same data*/

bool compareLists(struct node* head1, struct node *head2)

{

    struct node* temp1 = head1;

    struct node* temp2 = head2;

    while (temp1 && temp2)

    {

        if (temp1->data == temp2->data)

        {

            temp1 = temp1->next;

            temp2 = temp2->next;

        }

        else return 0;

    }

    /* Both are empty reurn 1*/

    if (temp1 == NULL && temp2 == NULL)

        return 1;

    /* Will reach here when one is NULL

      and other is not */

    return 0;

}

/* Push a node to linked list. Note that this function

  changes the head */

void push(struct node** head_ref, char new_data)

{

    /* allocate node */

    struct node* new_node =

        (struct node*) malloc(sizeof(struct node));

    /* put in the data */

    new_node->data = new_data;

    /* link the old list off the new node */

    new_node->next = (*head_ref);

    /* move the head to pochar to the new node */

    (*head_ref)    = new_node;

}

// A utility function to print a given linked list

void printList(struct node *ptr)

{

    while (ptr != NULL)

    {

        printf("%c->", ptr->data);

        ptr = ptr->next;

    }

    printf("NULL ");

}

/* Drier program to test above function*/

int main()

{

    /* Start with the empty list */

    struct node* head = NULL;

    char str[] = "abacaba";

    int i;

    for (i = 0; str[i] != ''; i++)

    {

       push(&head, str[i]);

       printList(head);

       isPalindrome(head)? printf("Is Palindrome "):

                           printf("Not Palindrome ");

    }

    return 0;

}


Output:


#include<stdio.h>

/* Function to calculate x raised to the power y */

int power(int x, unsigned int y)

{

    if (y == 0)

        return 1;

    else if (y%2 == 0)

        return power(x, y/2)*power(x, y/2);

    else

        return x*power(x, y/2)*power(x, y/2);

}

/* Program to test function power */

int main()

{

    int x = 2;

    unsigned int y = 3;

    printf("%d", power(x, y));

    return 0;

}

Hire Me For All Your Tutoring Needs
Integrity-first tutoring: clear explanations, guidance, and feedback.
Drop an Email at
drjack9650@gmail.com
Chat Now And Get Quote