0% found this document useful (0 votes)
12 views13 pages

DS Unit-1

The document explains structures and unions in C, highlighting their definitions, syntax, and differences. It also covers nested structures, arrays of structures, data structures classification, time and space complexities, and abstract data types (ADTs) with their operations. Additionally, it includes examples of sorting algorithms like Quick Sort and Merge Sort.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
12 views13 pages

DS Unit-1

The document explains structures and unions in C, highlighting their definitions, syntax, and differences. It also covers nested structures, arrays of structures, data structures classification, time and space complexities, and abstract data types (ADTs) with their operations. Additionally, it includes examples of sorting algorithms like Quick Sort and Merge Sort.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 13

Define structure.

Explain the creation of structure and structure


variables with examples.

A structure in C is a user-defined data type that allows grouping multiple related


variables of different data types under a single name. Unlike arrays, which hold only
one type of data, structures help store multiple types in an organized manner.

Syntax of a Structure:
struct StructureName {
data_type member1;
data_type member2;
...
};
struct is the keyword used to define a structure.
StructureName is the name of the structure.
member1, member2 are the variables (also called members of the structure).
Example Program:
#include <stdio.h>
Output:
// Defining a structure Roll No: 101
struct Student { Name: Alice
int rollNo; Marks: 85.50
char name[50];
float marks; The structure Student contains
}; three members: rollNo (integer),
name (string), and marks (float).
int main() { Inside main(), we declare s1, a
struct Student s1 = {101, "Alice", 85.5}; structure variable of type
printf("Roll No: %d\n", s1.rollNo); Student, and initialize it with
printf("Name: %s\n", s1.name); values.
printf("Marks: %.2f\n", s1.marks); The printf function accesses and
prints each member of the
return 0; structure.
}

We use the dot (.) operator to access structure members.


Multiple structure variables can be declared at once.
Define union. Compare union and structures with examples.
A union in C is a user-defined data type that, like a structure, can hold multiple
members of different data types. However, in a union, all members share the same
memory location, meaning only one member can store a value at a time.

Syntax of a Union:
union UnionName {
data_type member1;
data_type member2;
...
};

union is the keyword used to define a union.


UnionName is the name of the union.
member1, member2 are the variables (members) of the union.

Difference Between Structure and Union


Structure:
Allocates separate memory for each member.
The total size of a structure is the sum of all members' sizes.
Allows simultaneous access to all members.
Useful when multiple values need to be stored together.
Union:
Shares the same memory location among all members.
The total size of a union is equal to the size of its largest member.
Only one member can store a value at a time; assigning a new value overwrites
the previous one.
Efficient for memory optimization when only one value is needed at a time.
Example Program:
#include <stdio.h>

union Data {
int rollNo; // 4 bytes
float marks; // 4 bytes
double grade; // 8 bytes
}; Output:
Union:
int main() { Size: 8 bytes
union Data d1; Roll No: 101
Marks: 89.50
printf("Union:\n");
printf("Size: %lu bytes\n", sizeof(d1));

d1.rollNo = 101;
printf("Roll No: %d\n", d1.rollNo);

d1.marks = 89.5; // Overwrites previous value


printf("Marks: %.2f\n", d1.marks);

return 0;
}

Structure stores rollNo (4 bytes) and marks (4 bytes) separately, so the total
memory is 8 bytes.
Union has rollNo (4 bytes), marks (4 bytes), and grade (8 bytes), but it only
occupies 8 bytes because it takes the size of its largest member (double).
When a new value is assigned to a union member, the previous value is lost
because all members share the same memory space.
3. Illustrate the concept of nested structure with examples.
A nested structure in C is a structure inside another structure. It helps represent
complex data by combining related structures, making data organization easier and
improving code readability.

Types of Nested Structures:


1. Separated Nested Structure
2. Embedded Nested Structure

1. Separated Nested Structure :


In this type, the inner structure is defined separately from the outer structure, and a
variable of the inner structure is used inside the outer structure.

Example: Separated Nested Structure


#include <stdio.h>
struct Address {
char city[20];
int pincode;
};
Output :
struct Student { Name: Alice
int rollNo; City: New York
char name[50]; Pincode: 10001
struct Address addr;
};

int main() {
struct Student s1 = {101, "Alice", {"New York", 10001}};

printf("Name: %s\nCity: %s\nPincode: %d\n", s1.name, s1.addr.city,


s1.addr.pincode);

return 0;
}

Explanation:
The inner structure Address is defined separately.
The outer structure Student contains Address as a member.
This approach allows code reusability, as Address can be used in other
structures as well.
2. Embedded Nested Structure
In this type, the inner structure is defined inside the outer structure itself.
Example: Embedded Nested Structure :
#include <stdio.h>

struct Student {
int rollNo;
Output :
char name[50];
Name: Alice
City: Los Angeles
struct {
Pincode: 90001
char city[20];
int pincode;
} addr;
};

int main() {
struct Student s1 = {101, "Alice", {"Los Angeles", 90001}};

printf("Name: %s\nCity: %s\nPincode: %d\n", s1.name, s1.addr.city,


s1.addr.pincode);

return 0;
}

Explanation:
The inner structure is directly declared inside the outer structure.
This approach is useful when the inner structure is only relevant to the outer
structure and will not be used elsewhere.
Key Differences Between Separated and Embedded Nested Structures
Separated Nested Structure allows reusability of the inner structure.
Embedded Nested Structure is useful when the inner structure is used only
within the outer structure.
4. Explain about an array of structures with a suitable example.

An array of structures is a collection of multiple structure variables stored in a


single array. It allows handling multiple records of the same type efficiently, just like
an array of primitive data types.

Example Program :
#include <stdio.h>

struct Student { Output :


int rollNo; Roll No: 101
char name[50]; Name: Alice
float marks; Marks: 85.50
};
Roll No: 102
int main() { Name: Bob
struct Student s[3] = { Marks: 90.00
{101, "Alice", 85.5},
{102, "Bob", 90.0}, Roll No: 103
{103, "Charlie", 78.5} Name: Charlie
}; Marks: 78.50

for (int i = 0; i < 3; i++) {


printf("Roll No: %d\n", s[i].rollNo);
printf("Name: %s\n", s[i].name);
printf("Marks: %.2f\n\n", s[i].marks);
}

return 0;
}

The structure Student contains rollNo, name, and marks as members.


An array of structures s[3] is created to store three student records.
A loop is used to display the details of all students.

Advantages of an Array of Structures


Helps store and manage multiple records efficiently.
Provides better organization for structured data like student records, employee
details, etc.
Makes data retrieval and modification easier using loops.
5. Define data structure. Explain the classification of data
structures.
A data structure is a way of organizing and storing data so that it can be accessed
and manipulated efficiently. It helps in managing large amounts of data and
performing operations like searching, sorting, and updating effectively.

Classification of Data Structures


Data structures are broadly classified into two types:

1. Linear Data Structures


In linear data structures, elements are arranged sequentially, and each element is
connected to its previous and next element.

Examples of Linear Data Structures:


Array – A collection of elements stored in contiguous memory locations.
Stack – Follows LIFO (Last In, First Out) principle.
Queue – Follows FIFO (First In, First Out) principle.
Linked List – A sequence of nodes connected via pointers.

2. Non-Linear Data Structures


In non-linear data structures, elements are not stored sequentially and are
connected in a hierarchical or complex manner.

Examples of Non-Linear Data Structures:


Tree – A hierarchical structure consisting of nodes (e.g., Binary Tree, BST).
Graph – A collection of nodes (vertices) and edges connecting them.
Example Code: Using an Array (Linear Data Structure)
#include <stdio.h>

int main() {
int arr[5] = {10, 20, 30, 40, 50}; // Array declaration

printf("Array elements:\n");
for (int i = 0; i < 5; i++) { Output :
printf("%d ", arr[i]); Array elements:
} 10 20 30 40 50

return 0;
}
Key Differences Between Linear and Non-Linear Data Structures :

Linear structures are simple to implement but have higher time complexity for some
operations.
Non-linear structures provide efficient searching and organization, especially in
complex data handling.
6. Explain time and space complexities in data structures.
Time Complexity
Time complexity refers to the amount of time an algorithm takes to complete based
on the input size (n). It helps in evaluating the efficiency of an algorithm.
Types of Time Complexities:
1. Best Case Complexity: Minimum time required for execution (e.g., already sorted
array in Bubble Sort).
2. Worst Case Complexity: Maximum time required for execution (e.g., reversed
array in Bubble Sort).
3. Average Case Complexity: The expected time for random inputs.
Example:
Searching for an element in an array of size n using linear search takes O(n) time,
as we might need to check all elements.
Searching in a sorted array using binary search takes O(log n) time, as it divides
the array into halves.
Big-O Notation for Common Algorithms:
O(1) – Constant Time: Accessing an array element (arr[i]).
O(n) – Linear Time: Traversing an array (for loop from 0 to n).
O(log n) – Logarithmic Time: Binary Search.
O(n²) – Quadratic Time: Nested loops in sorting (Bubble Sort).

Space Complexity
Space complexity refers to the amount of memory used by an algorithm during
execution. This includes:
1. Fixed Part: Memory required for constants, variables, and program instructions.
2. Variable Part: Memory required for dynamic allocation (e.g., recursion, arrays,
linked lists).
Types of Space Complexities:
O(1) – Constant Space: Uses a fixed amount of memory. Example: Swapping two
numbers.
O(n) – Linear Space: Uses memory proportional to input size. Example: Storing an
array of size n.
Example:
A recursive function requires additional stack memory for each function call,
increasing space complexity.
Example : Array Traversal (Time Complexity O(n)) :
#include <stdio.h>

void traverseArray(int arr[], int n) {


for (int i = 0; i < n; i++) {
printf("%d ", arr[i]);
}
}

int main() {
int arr[] = {10, 20, 30, 40, 50};
int size = sizeof(arr) / sizeof(arr[0]);

traverseArray(arr, size);
return 0;
}

Time Complexity: O(n) (Linear) since it loops through n elements.


Space Complexity: O(1) (Constant) as it uses only a few extra variables.

Time Complexity measures how fast an algorithm runs.


Space Complexity measures how much memory an algorithm uses.
Optimizing both improves program efficiency.
7. Define ADT (Abstract Data Type). Explain different ADTs
with their operations.
An Abstract Data Type (ADT) is a data structure that is defined by its operations, not
by its implementation. It provides a way to organize and manipulate data without
specifying the underlying storage method.

Types of ADTs :
1. Linear Data Structures
Linear data structures store elements sequentially, and each element is connected
to its previous and next element.
Types of linear data structures :
Array – Stores elements in adjacent memory locations.
Stack – Follows LIFO (Last In, First Out) principle.
Queue – Follows FIFO (First In, First Out) principle.
Linked List – A sequence of nodes connected via pointers.
2. Stack ADT
A stack is a linear data structure that follows LIFO (Last In, First Out) principle.
Operations of Stack ADT :
Push(): Inserts an element at the top of the stack.
Pop(): Removes and returns the top element.
Peek(): Returns the top element without removing it.
IsEmpty(): Checks if the stack is empty.
Stack follows sequential memory allocation and is useful in function calls, undo
mechanisms, and expression evaluation.
3. Queue ADT
A queue is a linear data structure that follows FIFO (First In, First Out) principle.
Operations of Queue ADT (From PPTs):
Enqueue(x): Adds an element to the rear of the queue.
Dequeue(): Removes and returns the front element.
Front(): Returns the front element without removing it.
IsEmpty(): Checks if the queue is empty.
Queues are used in scheduling, data buffering, and handling requests in order.
4. Linked List ADT
A linked list is a collection of nodes where each node contains a data field and a
pointer to the next node.
Types of Linked Lists :
Singly Linked List: Each node points to the next node.
Doubly Linked List: Each node points to both next and previous nodes.
Circular Linked List: The last node connects to the first node.
Linked lists provide dynamic memory allocation and efficient insertions/deletions.
5. Abstract Data Types
Stack ADT
Queue ADT
List ADT
Linked List ADT
Each ADT defines a set of operations without specifying how the data is stored
internally.

8. Sort the following elements using Quick Sort and also write the C
program to implement the Quick Sort algorithm.
#include <stdio.h>

int main() {
void swap(int *a, int *b) {
int arr[] = {75, 45, 40, 80, 35, 78, 98, 30, 39,
int temp = *a;
100};
*a = *b;
int n = sizeof(arr) / sizeof(arr[0]);
*b = temp;
}
printArray(arr, n);
quickSort(arr, 0, n - 1);
int partition(int arr[], int low, int high) {
printArray(arr, n);
int pivot = arr[high], i = low - 1, j;
for (j = low; j < high; j++) {
return 0;
if (arr[j] < pivot) {
}
i++;
swap(&arr[i], &arr[j]);
} Output :
} 75 45 40 80 35 78 98 30 39 100
swap(&arr[i + 1], &arr[high]); 30 35 39 40 45 75 78 80 98 100
return i + 1;
}

void quickSort(int arr[], int low, int high) {


if (low < high) {
int pi = partition(arr, low, high);
quickSort(arr, low, pi - 1);
quickSort(arr, pi + 1, high);
}
}

void printArray(int arr[], int size) {


for (int i = 0; i < size; i++)
printf("%d ", arr[i]);
printf("\n");
}
9. Sort the following elements using Merge Sort and also write the C
program to implement the Merge Sort algorithm.
#include <stdio.h>

void merge(int arr[], int left, int mid, int right)


{
int i, j, k, n1 = mid - left + 1, n2 = right - mid;
int L[n1], R[n2];

int main() {
for (i = 0; i < n1; i++)
int arr[] = {75, 45, 40, 80, 35, 78, 98, 30, 39,
L[i] = arr[left + i];
100};
for (j = 0; j < n2; j++)
int n = sizeof(arr) / sizeof(arr[0]);
R[j] = arr[mid + 1 + j];

printArray(arr, n);
i = 0, j = 0, k = left;
mergeSort(arr, 0, n - 1);
while (i < n1 && j < n2) {
printArray(arr, n);
if (L[i] <= R[j])
arr[k++] = L[i++];
return 0;
else
}
arr[k++] = R[j++];
}

while (i < n1) Output :


arr[k++] = L[i++]; 75 45 40 80 35 78 98 30 39 100
while (j < n2) 30 35 39 40 45 75 78 80 98 100
arr[k++] = R[j++];
}

void mergeSort(int arr[], int left, int right) {


if (left < right) {
int mid = left + (right - left) / 2;
mergeSort(arr, left, mid);
mergeSort(arr, mid + 1, right);
merge(arr, left, mid, right);
}
}

void printArray(int arr[], int size) {


for (int i = 0; i < size; i++)
printf("%d ", arr[i]);
printf("\n");
}
10. Sort the following elements using Radix Sort and also write the C
program to implement the Radix Sort algorithm.
#include <stdio.h>

int getMax(int arr[], int n) {


int max = arr[0];
for (int i = 1; i < n; i++)
if (arr[i] > max)
max = arr[i];
return max;
}

void countingSort(int arr[], int n, int exp) {


int output[n], count[10] = {0}, i;

for (i = 0; i < n; i++)


count[(arr[i] / exp) % 10]++;

for (i = 1; i < 10; i++)


count[i] += count[i - 1];

for (i = n - 1; i >= 0; i--) {


output[count[(arr[i] / exp) % 10] - 1] =
arr[i];
count[(arr[i] / exp) % 10]--;
} int main() {
int arr[] = {798, 89, 697, 8421, 9, 520};
for (i = 0; i < n; i++) int n = sizeof(arr) / sizeof(arr[0]);
arr[i] = output[i];
} printArray(arr, n);
radixSort(arr, n);
void radixSort(int arr[], int n) { printArray(arr, n);
int max = getMax(arr, n);
for (int exp = 1; max / exp > 0; exp *= 10) return 0;
countingSort(arr, n, exp); }
}
Output :
void printArray(int arr[], int n) { 798 89 697 8421 9 520
for (int i = 0; i < n; i++) 9 89 520 697 798 8421
printf("%d ", arr[i]);
printf("\n");
}

You might also like