Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Array Text corrections and updations - shrinivaskane #123

Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 18 additions & 11 deletions array/README.md
Original file line number Diff line number Diff line change
@@ -1,26 +1,29 @@
# Array

Arrays are a basic and essential data structure in computer science. They consist of a fixed-size contiguous memory block and offer O(1) read and write time complexity. As a fundamental element of programming languages, arrays come built-in in their core.
Arrays are a fundamental and essential data structure in computer science. They consist of a fixed-size contiguous memory block and offer O(1) read and write time complexity. As a fundamental element of programming languages, arrays come built-in with their core.

To provide a real-world analogy, consider an array of athletes preparing for a sprinting match. Each athlete occupies a specific position within the array, typically denoted as 1, 2,…, n. While it is technically possible for each athlete to be in a different position, the positions generally carry some form of significance, such as alphabetical order or seniority within the sport.

## Implementation

In the Go programming language, arrays are considered values rather than pointers and represent the entirety of the array. Whenever an array is passed to a function, a copy is created, resulting in additional memory usage. To avoid this it is possible to pass a pointer to an array, or use slices instead. The size of the array is constant and it must be known at compile time, and there is no need to use the built-in `make` function when defining arrays.
In the Go programming language, arrays are considered values rather than pointers and represent the entirety of the array. Whenever an array is passed to a function, a copy is created, resulting in additional memory usage. To avoid this, it is possible to pass a pointer to an array, or use slices instead. The size of the array is constant and it must be known at compile time, and there is no need to use the built-in `make` function when defining arrays.

```Go
package main

import "fmt"

func main() {
// Declare an array with 2 int elements, defaulting to 0.
var nums1 [2]int
// Initialize an array with 3 int elements.
nums2 := [3]int{1, 2, 3}
// Print both arrays.
fmt.Println(nums1, nums2) // Prints [0 0] [1 2 3]
}
```

Although arrays are fundamental data structures in Go, their constant size can make them inflexible and difficult to use in situations where a variable size is required. To address this issue, Go provides [slices](https://blog.golang.org/slices-intro), an abstraction of arrays that offer more convenient access to sequential data typically stored in arrays. When a slice is passed to a function, the head of the slice is replaced but the slice still points to the same data, hence it is possible for the callee to modify the values of the slice and send them back to the caller.
Although arrays are fundamental data structures in Go, their constant size can make them inflexible and difficult to use in situations where a variable size is required. To address this issue, Go provides [slices](https://blog.golang.org/slices-intro), an abstraction of arrays that offer more convenient access to sequential data typically stored in arrays. When a slice is passed to a function, only the slice header is passed, but it still references the same underlying array data, hence it is possible for the callee to modify the values of the slice and send them back to the caller.

Slices enable adding values using the `append` function, allowing dynamic resizing. Additionally, selectors of the format [low:high] can be used to select or manipulate data in the slice. By utilizing slices instead of arrays, Go programmers gain a more flexible and powerful tool to manage their data structures.

Expand All @@ -30,10 +33,11 @@ package main
import "fmt"

func main() {
// Create a slice with elements 1, 2, 3.
nums := []int{1, 2, 3}
nums = append([]int{0}, nums...) // Add new element to the start
nums = append(nums, 4) // Add new element to the end
nums = nums[:len(nums)-1] // Removes last element
nums = append([]int{0}, nums...) // Add a new element to the start
nums = append(nums, 4) // Add a new element to the end
nums = nums[:len(nums)-1] // Removes the last element
fmt.Println(nums) // Prints [0 1 2 3]
}
```
Expand All @@ -60,12 +64,15 @@ package main
import "fmt"

func main() {
// Initialize a slice with 6 elements.
nums := []int{1, 2, 3, 4, 5, 6}
nums = nums[:len(nums)-1] // drop last element
nums = nums[1:] // drop first element
nums = nums[1:] // all elements from index 1 to the end
nums = nums[:2] // all elements from index 0 to 1
nums = nums[1:2] // the element at index 1
// Sequentially modify the slice.
nums = nums[:len(nums)-1] // Drop the last element
nums = nums[1:] // Drop the first element
nums = nums[1:] // Keep all elements from index 1 to the end
nums = nums[:2] // Keep all elements up to (but not including) index 2
nums = nums[1:2] // Keep only the element at index 1
// Print final slice.
fmt.Println(nums) // Prints [4]
}
```
Expand Down
17 changes: 13 additions & 4 deletions array/bubble_sort.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,20 @@ package array

// BubbleSort solves the problem in O(n^2) time and O(1) space.
func BubbleSort(input []int) {
for i := range input {
for j := range input {
if input[i] < input[j] {
input[i], input[j] = input[j], input[i]
n := len(input)
for i := 0; i < n-1; i++ {
// flag to check if there were any swaps made
swapped := false
// loop can run until n-i-1 since last i elements are already sorted in ith pass
for j := 0; j < n-i-1; j++ {
if input[j] > input[j+1] {
input[j], input[j+1] = input[j+1], input[j]
swapped = true
}
}
if !swapped {
// if no swaps were made, array is already sorted
break
}
}
}
8 changes: 8 additions & 0 deletions array/find_duplicate_in_array.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,16 @@ package array

// FindDuplicate solves the problem in O(n) time and O(1) space.
func FindDuplicate(list []int) int {
if len(list) == 0 {
return -1
}

for _, item := range list {
itemIndex := item - 1
// Check for Invalid index if any, return -1 indicating an error.
if itemIndex < 0 || itemIndex >= len(list) {
return -1
}
if list[itemIndex] < 0 {
return list[itemIndex] * -1
}
Expand Down
5 changes: 5 additions & 0 deletions array/reverse_inplace.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,11 @@ package array

// ReverseInPlace solves the problem in O(n) time and O(1) space.
func ReverseInPlace(list []int, start, end int) {
// validation of input
if start < 0 || end >= len(list) || start > end {
// if indices are invalid, do nothing
return
}
for i := start; i <= start+end/2 && i < end-i+start; i++ {
list[i], list[end-i+start] = list[end-i+start], list[i]
}
Expand Down
7 changes: 1 addition & 6 deletions queue/circular_queue_using_array.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,13 +17,8 @@ var ErrQueueAtMaxCapacity = errors.New("queue is at max capacity")

// NewCircularQueue returns a fixed size circular queue.
func NewCircularQueue(size int) *CircularQueue {
circular := make([]int, size)
for i := range circular {
circular[i] = emptyValue
}

return &CircularQueue{
data: circular,
data: make([]int, size),
rear: -1,
size: 0,
front: 0,
Expand Down
20 changes: 8 additions & 12 deletions recursion/is_palindrome.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,13 @@ package recursion

// IsPalindrome solves the problem in O(n) time and O(n) space.
func IsPalindrome(s string) bool {
if len(s) < 2 {
return true
left, right := 0, len(s)-1
for left < right {
if s[left] != s[right] {
return false
}
left++
right--
}

if len(s) == 2 {
return s[0] == s[1]
}

if s[0] != s[len(s)-1] {
return false
}

return IsPalindrome(s[1 : len(s)-1])
return true
}
16 changes: 11 additions & 5 deletions recursion/multiplication.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,19 @@ package recursion

// Multiply solves the problem in O(b) time and O(1) space.
func Multiply(a, b int) int {
if b == 0 {
return 0
result := 0
negative := b < 0
if negative {
b = -b
}

if b < 0 {
return -Multiply(a, -b)
for b > 0 {
result += a
b--
}

return a + Multiply(a, b-1)
if negative {
return -result
}
return result
}
25 changes: 11 additions & 14 deletions stack/balancing_symbols.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,42 +6,39 @@ var (
'(': ')',
'{': '}',
}

// stack retains the opener symbols e.g. [({.
stack []rune
)

// IsExpressionBalanced solves the problem in O(n) time and O(n) space.
func IsExpressionBalanced(s string) bool {
stack = []rune{}
if s == "" {
return true
}
// stack retains the opener symbols e.g. [({.
stack := []rune{} // Localized stack

for _, c := range s {
if _, ok := symbols[c]; ok {
push(c)
stack = push(stack, c)
continue
}

if len(stack) == 0 {
return false // More closers than openers
}

lastOpener := pop()
var lastOpener rune
stack, lastOpener = pop(stack)
if symbols[lastOpener] != c {
return false // opener did not match the last closer
return false // Opener did not match the last closer
}
}

return len(stack) == 0
}

func push(a rune) {
stack = append(stack, a)
func push(stack []rune, a rune) []rune {
return append(stack, a)
}

func pop() rune {
func pop(stack []rune) ([]rune, rune) {
tmp := stack[len(stack)-1]
stack = stack[:len(stack)-1]
return tmp
return stack, tmp
}
30 changes: 16 additions & 14 deletions strings/longest_dictionary_word.go
Original file line number Diff line number Diff line change
@@ -1,27 +1,29 @@
package strings

import "strings"

// LongestDictionaryWordContainingKey solves the problem in O(n) time and O(1) space.
func LongestDictionaryWordContainingKey(key string, dic []string) string {
keyNum := hash(key)
longest := ""
keyCharCount := make(map[rune]int)
for _, char := range key {
keyCharCount[char]++
}

var longest string
for _, word := range dic {
wordNum := hash(word)
if keyNum&wordNum == keyNum {
if len(longest) < len(word) {
longest = word
}
if containsAllChars(word, keyCharCount) && len(word) > len(longest) {
longest = word
}
}
return longest
}

// hash turns a string into a number
// the output for "abc", "acb", "cba" and etc... are all the same.
func hash(s string) rune {
var res rune
for _, w := range s {
res |= w
// function to check if word contains all characters in the key.
func containsAllChars(word string, keyCharCount map[rune]int) bool {
for char, count := range keyCharCount {
if strings.Count(word, string(char)) < count {
return false
}
}
return res
return true
}
11 changes: 7 additions & 4 deletions strings/look_and_tell.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,22 +17,25 @@ func LookAndTell(depth int) []string {
}

for i := 1; i < depth; i++ {
output = append(output, tell(output[i-1]))
output = append(output, generateNext(output[i-1]))
}
return output
}

func tell(n string) string {
// generateNext generates the next number in the sequence.
func generateNext(n string) string {
var step, what string
var count, until int
for until < len(n) {
count, what, until = findHowMany(n, until)
count, what, until = countConsequtiveDigits(n, until)
step += strconv.Itoa(count) + what
}
return step
}

func findHowMany(n string, until int) (int, string, int) {
// counts the consecutive occurrences of a digit in a string,from a given position.
// returning count, digit and the new position.
func countConsequtiveDigits(n string, until int) (int, string, int) {
last := ""
count := 0
for until < len(n) {
Expand Down
2 changes: 1 addition & 1 deletion strings/number_in_english.go
Original file line number Diff line number Diff line change
Expand Up @@ -104,5 +104,5 @@ func howMany(num, level int) int {
if num < level {
return -1
}
return int(float64(num / level))
return num / level
}
3 changes: 2 additions & 1 deletion tree/sorted_array_to_balanced_bsd.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package tree

// BalancedBinarySearchTree solves the problem in O(n) time and O(n) space.
// BalancedBinarySearchTree solves the problem in O(n) time and O(n) space for the tree
// and O(log n) for the recursion stack (for a balanced tree).
func BalancedBinarySearchTree(sorted []int) *BinaryTreeNode {
if len(sorted) == 0 {
return nil
Expand Down