Skip to content

Commit

Permalink
Single linked list playground
Browse files Browse the repository at this point in the history
Add single linked list test playground into repository
  • Loading branch information
zhaohuixing committed Feb 10, 2019
1 parent 8a0be3f commit 8fc63e6
Show file tree
Hide file tree
Showing 10 changed files with 617 additions and 0 deletions.
Binary file modified .DS_Store
Binary file not shown.
189 changes: 189 additions & 0 deletions SingleLList.playground/Contents.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,189 @@
//import Cocoa

var str = "Hello, playground"

typealias CSingleLinkedListNodeInt = CSingleLinkedListNode<Int>

let node1 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 12)
let node2 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 28)
let node3 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 14)
let node4 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 15)
let node5 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 16)
let node6 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 17)
node2.next = node3;
node3.next = node4;
node4.next = node5;
node5.next = node6;
node1.next = node2;
let nodec6 = node6.clone()

print("LList node list")
var tempNode : CSingleLinkedListNodeInt? = node1
while tempNode != nil {
print(tempNode!.data)
tempNode = tempNode?.next
}

print(node1.next!.data!)
print((node1.data!))
print((node1.tail!.data!))
print((node1.tail!.next?.data!) ?? "nil object") //The "?? nil object" clause is for avoiding warning "Expression implicitly coerced from 'Int?' to 'Any'" by provding a default value to avoid this warning */
print((node1.tail!.next?.data!) as Any) //The "as Any" clause is for avoiding warning "Expression implicitly coerced from 'Int?' to 'Any'" by Explicitly casting to 'Any' with 'as Any' to silence this warning
//print((node1.tail!.next?.data!)!) //The last "!" clause is for avoiding warning "Expression implicitly coerced from 'Int?' to 'Any'" by Force-unwrapping the value to avoid this warning. But this gets execution exception: "error: Execution was interrupted, reason: EXC_BAD_INSTRUCTION (code=EXC_I386_INVOP, subcode=0x0)"
print((node1.tail!.next?.data!)) //This is sample of unwrapping warning
//print((node1.tail!.next!.data!)) //Exectuion exception: Fatal error: Unexpectedly found nil while unwrapping an Optional value

print(nodec6.data!)
let nodec1 = node1.clone()
print((nodec1.data!))
print((nodec1.tail!.data!))

typealias CSingleLinkedListInt = CSingleLinkedList<Int>
typealias STSingleLinkedListInt = STSingleLinkedList<Int>

let csllist1 = CSingleLinkedListInt(head:node1)
let cllhead = csllist1.head
print((cllhead?.data!) ?? "CSingleLinkedList head is nill") //If replace "cllhead?" with "cllhead!", then the execution exception will be thrown when cllhead is nill
print((cllhead?.tail!.data!) ?? "CSingleLinkedList tail is nill")
print((csllist1.tail!.data!))
print(csllist1.count)
print((csllist1[14]?.data) ?? "CSingleLinkedList [14] is not existed")
print((csllist1[914]?.data) ?? "CSingleLinkedList [914] is not existed")

csllist1.reverse()

print("LList node list")
tempNode = csllist1.head
while tempNode != nil {
print(tempNode!.data)
tempNode = tempNode?.next
}

csllist1.reverse2()

print("LList node list after reverse2")
tempNode = csllist1.head
while tempNode != nil {
print(tempNode!.data)
tempNode = tempNode?.next
}

print("End print LList node list after reverse2")

csllist1.reverseBetween(start:1, end: 5)

print("LList node list after reverseBetween")
tempNode = csllist1.head
while tempNode != nil {
print(tempNode!.data)
tempNode = tempNode?.next
}

print("End print LList node list after reverseBetween")


var ssllist1 = STSingleLinkedListInt(head:nodec1)
let sllhead = ssllist1.head
print((sllhead?.data!) ?? "STSingleLinkedList head is nill") //If replace "cllhead?" with "cllhead!", then the execution exception will be thrown when cllhead is nill
print((sllhead?.tail!.data!) ?? "STSingleLinkedList tail is nill")
print((ssllist1.tail!.data!))
print((ssllist1.count))
print((ssllist1[28]?.data) ?? "STSingleLinkedList [28] is not existed")
print((ssllist1[285]?.data) ?? "STSingleLinkedList [285] is not existed")

ssllist1.reverse()

print("\n\nstruct type LList node list not unwrapped with comiling warning, ouput as Optional(X)")
tempNode = ssllist1.head
while tempNode != nil {
print(tempNode!.data)
tempNode = tempNode?.next
}

print("\n\nstruct type LList node list unwrapped without compiling warning, outout no Optional(X)")
tempNode = ssllist1.head
while tempNode != nil {
print(tempNode!.data!)
tempNode = tempNode?.next
}

if csllist1.iscycled().retFlag == false {
print("csllist1 is not cycled")
}
else {
print("csllist1 is cycled")
}

let n1 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 12)
let n2 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 28)
let n3 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 14)
let n4 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 15)
let n5 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 16)
let n6 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 17)
n2.next = n3;
n3.next = n4;
n4.next = n5;
n5.next = n6;
n6.next = n3;
n1.next = n2;

let nR1 = n1.iscycled()
if nR1.retFlag == false {
print("n1 is not cycled")
}
else {
print("n1 is cycled")
print("n1 cycled node: \(String(describing: nR1.cycleNode?.data))")
print("n1 tail node: \(nR1.tailNode?.data ?? 0)")
}

let x1 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 12)
let x2 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 28)
let x3 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 14)
let x4 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 15)
let x5 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 16)
let x6 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 17)
x2.next = x3;
x3.next = x4;
x4.next = x5;
x5.next = x6;
x1.next = x2;

var xlist = CSingleLinkedListInt(head:x1)
print("XList node list before")

tempNode = xlist.head
while tempNode != nil {
print(tempNode!.data!)
tempNode = tempNode?.next
}

let x0 : CSingleLinkedListNodeInt = CSingleLinkedListNodeInt(data: 6)
xlist.AddHead(head:x0)

print("XList node list Addhead without default value prvoided with compiling warning, output as Optional(X)")

tempNode = xlist.head
while tempNode != nil {
print(tempNode!.data)
tempNode = tempNode?.next
}

print("XList node list Addhead with default value, output no Optional(X), no compiling warning")

tempNode = xlist.head
while tempNode != nil {
print(tempNode!.data ?? "Nil value reached")
tempNode = tempNode?.next
}

xlist.RemoveHead()

print("XList node list RemoveHead")

tempNode = xlist.head
while tempNode != nil {
print(tempNode!.data)
tempNode = tempNode?.next
}

182 changes: 182 additions & 0 deletions SingleLList.playground/Sources/CSingleLList.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,182 @@
//
// CSingleLList.swift
// LinkList
//
// Created by Zhaohui Xing on 10/26/18.
// Copyright © 2018 Zhaohui Xing. All rights reserved.
//
import Foundation

//class base sll as reference type
public class CSingleLinkedList<T : Equatable> { //Equatable for ! operator in line#60
var m_Head: CSingleLinkedListNode<T>?
var m_Tail: CSingleLinkedListNode<T>?

init() {
}

public init(head: CSingleLinkedListNode<T>) {
self.m_Head = head
self.m_Tail = self.m_Head?.tail
}
}

extension CSingleLinkedList {
public var head : CSingleLinkedListNode<T>? {
get {
return m_Head
}
set (newNode) {
m_Head = newNode;
m_Tail = newNode?.tail
}
}
}

extension CSingleLinkedList {
public var tail : CSingleLinkedListNode<T>? {
return m_Tail
}
}

extension CSingleLinkedList {
public var count : Int {
var nCount : Int = 0
var cur : CSingleLinkedListNode<T>? = m_Head

while cur != nil {
cur = cur?.next
nCount += 1
}

return nCount
}
}

extension CSingleLinkedList {
public subscript (value : T) -> CSingleLinkedListNode<T>? {
var cur : CSingleLinkedListNode<T>? = m_Head

while cur != nil && cur!.data != value {
cur = cur?.next
}

return cur
}
}

extension CSingleLinkedList {
public func reverse() {
let prev : CSingleLinkedListNode<T>? = CSingleLinkedListNode<T>(); //This avoid the tail node is nil and while loop cannot go through all nodes
prev?.next = m_Head //prev.next as temperory head shifting cursor
let cur : CSingleLinkedListNode<T>? = m_Head //Using cur.next as moving cursor, Note: this approach the orginal head's next is altered after the loop

while cur?.next != nil {
let temp: CSingleLinkedListNode<T>? = cur?.next
cur?.next = temp?.next;
temp?.next = prev?.next
prev?.next = temp
}
m_Head = prev?.next
}
}

extension CSingleLinkedList {
public func reverse2() {
let prev : CSingleLinkedListNode<T>? = CSingleLinkedListNode<T>(); //This avoid the tail node is nil and while loop cannot go through all nodes
prev?.next = m_Head //prev.next as temperory head shifting cursor
var cur : CSingleLinkedListNode<T>? = m_Head?.next //Using cur as moving cursor

while cur != nil {
let temp: CSingleLinkedListNode<T>? = cur
cur = temp?.next;
temp?.next = prev?.next
prev?.next = temp
}
m_Head?.next = nil; //This one need this call, since using cur as moving cursor and orginal head.next is not altered
m_Head = prev?.next
}
}

extension CSingleLinkedList {
public func iscycled()->(retFlag : Bool, cycleNode:CSingleLinkedListNode<T>?, tailNode:CSingleLinkedListNode<T>?) {
var bRet : (retFlag : Bool, cycleNode:CSingleLinkedListNode<T>?, tailNode:CSingleLinkedListNode<T>?) = (false, nil, nil)

if m_Head != nil {
bRet = m_Head!.iscycled()
}

return bRet
}
}

extension CSingleLinkedList {
public func AddHead(head: CSingleLinkedListNode<T>) {
head.next = m_Head;
m_Head = head;
}
}

extension CSingleLinkedList {
public func RemoveHead() {
m_Head = m_Head?.next;
}
}

extension CSingleLinkedList {
public func Append(value: CSingleLinkedListNode<T>) {
if self.head == nil {
self.head = value
}
else {
m_Tail?.next = value
m_Tail = value
}
}
}

extension CSingleLinkedList {
public func reverseBetween(start startIndex: Int, end endIndex: Int) {
if endIndex <= startIndex {
return
}

var cur : CSingleLinkedListNode<T>? = m_Head

//tempPrev is the start node to swap sequence.
var tempPrev : CSingleLinkedListNode<T>? //"?" allowing following calling "tempPrev = nil", otherwise compiling error for it
tempPrev = nil

let steps : Int = (0 < startIndex) ? startIndex-1 : 0
for _ in 0...steps {
if cur != nil {
tempPrev = cur
cur = cur?.next;
}
}
if cur == nil {
return
}

var tempHead: CSingleLinkedListNode<T>? = cur;


for _ in startIndex...(endIndex-1) {
if cur?.next != nil {
let temp: CSingleLinkedListNode<T>? = cur?.next
cur?.next = temp?.next;
temp?.next = tempHead
tempHead = temp
}
}

if tempPrev != nil {
tempPrev?.next = tempHead
}
else {
m_Head = tempHead
}

}
}

Loading

0 comments on commit 8fc63e6

Please sign in to comment.