标签:
1.栈的定义
栈是一种和列表类似的数据结构,可以用它来解决很多的编程问题,栈是一种高效的数据结构,因为数据只能在栈的顶端添加或者删除,所以这样的操作很快而且容易实现。
栈是一种特殊的列表,站内的元素只能拖过列表的一端进行访问,这一端陈伟栈顶。一叠盘子是最常见的栈结构,只能从顶部取盘子,洗好的盘子也只能放在顶端。栈被称为后入先出的数据结构。
由于栈具有后入先出的特点,所以任何不在栈顶的元素都无法访问。为了得到栈底的元素,必须拿掉上面的元素。
对栈的操作有将一个元素压入栈和将一个元素弹出栈。压入栈使用push()方法,弹出栈使用pop()方法。还有一个方法是预览栈顶元素,使用pop()方法虽然可以访问栈顶的元素,但是调用该方法后栈顶的元素将被永久的删除。peek()方法只范围栈顶的元素,而不删除它。
为了记录栈顶元素的位置,同时也为了标记从哪里可以加入新元素,我们使用变量top,当向栈内压入元素是该变量增大,从站内弹出元素时,该变量减小。
pop(),push(),peek()方法是最主要的三个方法,同时定义clear()方法可以清楚栈内所有的元素,length属性定义栈内元素的个数,同时定义一个empty属性标识栈内是否还有元素,不过使用length属性可以达到同样的目的。
栈结构的代码如下:
//使用数组dataStore保存站内元素,构造函数将其初始化为一个空数组。 //变量top定义栈顶的位置,构造时初始化为0,表示栈的起始位置为0 function Stack(){ this.dataStore = []; this.top = 0; this.push = push; this.pop = pop; this.peek = peek; this.clear = clear; this.length = length; //注意++操作符的位置,它放在this.top的后面,这样新入栈的元素就被放在top的当前位置对应的位置,同时top自加1,指向下一个位置 function push(element){ this.dataStore[this.top++] = element; } //返回栈顶元素,同时top的位置减1 function pop(){ return this.dataStore[--this.top]; } //peek()方法返回数组的第top-1个位置的元素,即栈顶元素 function peek(){ return this.dataStore[this.top-1]; } //将top的值设置0,即清空一个栈 function clear(){ this.top = 0; } //返回变量top的值即为栈内元素的个数 function length(){ return this.top; } }
使用下面的代码来检验栈结构
var s = new Stack(); s.push("David"); s.push("Baymond"); s.push("Bryan"); document.writeln("length:" + s.length()); document.writeln(s.peek()); var popped = s.pop(); document.writeln("the popped element is:" + popped); document.writeln(s.peek()); s.push("Cynthia"); document.writeln(s.peek()); s.clear(); document.writeln("length:" + s.length()); document.writeln(s.peek()); s.push("Clayton"); document.writeln(s.peek());
输出如下:
length:3
Bryan
the popped element is:Bryan
Baymond
Cynthia
length:0
undefined
Clayton
2.用栈实现进制转换
可以使用栈将一个数字从一种数制转换成另一种数制,假设想将数字n转换为以b为基数的数字,实现方法如下:
(1)最高位为n%b,将此位压入栈
(2)使用n/b代替n
(3)重复(1),(2)直到n等于0,且没有余数
(4)持续将站内元素弹出,直达栈为空,依次将这些元素排列,就得到转换后的数字的字符串形式
来看下面的代码,如何将数字转换为2进制和8进制
function mulBase(num,base){ var s = new Stack(); do{ s.push(num % base); num = Math.floor( num /= base ); }while(num>0); var converted = ""; while (s.length()>0){ converted += s.pop(); } return converted; } var num = 32; var base = 2; var newNum = mulBase(num, base); document.writeln(num + " converted to base " + base + " is " + newNum); num = 125; base = 8; newNum = mulBase(num, base); document.writeln(num + " converted to base " + base + " is " + newNum);
最后输出的结果如下:
32 converted to base 2 is 100000 125 converted to base 8 is 175
3.用栈判断回文
回文是这样一种现象:一个单词,短语或者数字,从前往后和从后往前写都是一样的。比如单词“dad”,“racecar”就是回文;如果忽略空格和标点符号,下面这个句子也是回文,“A man, a plan, a canal: Panama”,数字1001也是回文。
使用栈可以轻松的判断一个字符是否是回文。我们将拿到的字符串的每个字符按照从左至右的顺序入栈,当所有字符都入栈之后站内就保存了一个反转后的字符串,最后的字符在栈顶,第一个在栈尾。字符串完全压入站内后,通过持续弹出栈中的每个字母就可以的大一个新的字符串,该字符串刚好与原来的字符串顺序相反。我们只要比较这两个字符串即可,如果他们相等就说明这个是一个回文。代码如下:
function isPalindrome(word){ var s = new Stack(); for (var i=0; i<word.length; ++i) { s.push(word[i]); } var reword = ""; while(s.length()>0){ reword += s.pop(); } if(word == reword){ return true; }else{ return false; } } var word = "hello"; if(isPalindrome(word)){ document.writeln(word + " is a palindrome."); }else{ document.writeln(word + " is not a palindrome"); } word = "racecar"; if(isPalindrome(word)){ document.writeln(word + " is a palindrome."); }else{ document.writeln(word + " is not a palindrome"); }
输出结果如下:
hello is not a palindrome
racecar is a palindrome.
4.用栈实现递归
递归是一种很常见的算法,使用栈来实现递归是一件很轻松的事情,例如计算阶乘可以使用递归算法,如下:
function factorial(n) { if (n === 0) { return 1; } else { return n * factorial(n-1); } }
使用栈来模拟阶乘过程,例如:首先将5到1压入栈内,然后使用给一个循环,将数字一次弹出连乘就得到正确的答案,代码如下:
function fact(n){ var s = new Stack(); while (n>1){ s.push(n--); } var product = 1; while (s.length()>0){ product *= s.pop(); } return product; } document.writeln(fact(5));
结果如下:
120
标签:
原文地址:http://www.cnblogs.com/tylerdonet/p/5801248.html