我正在學習關于演算法和資料結構的簡短初學者課程。講師的語言是Python;我正在將代碼示例轉換為 JavaScript。到目前為止,一切都很好。
我正在處理鏈接串列。講師使用 Python 的 __repr__()方法測驗代碼。經過幾天的反復試驗,我有了一個有效的 JS 解決方案,但它與 Python 代碼并不完全相同。我想知道是否有更好的方法來實作我提供的 JS 代碼以及 Python 代碼。
Python
# class LinkedList and its methods are presumed to exist
def __repr__(self):
nodes = []
current = self.head
while current:
if current is self.head:
nodes.append("[Head: %s]" % current.data)
elif current.next_node is None:
nodes.append("[Tail: %s]" % current.data)
else
nodes.append("[%s]" % current.data)
current = current.next_node
return '-> '.join(nodes)
# running script
>>> l = LinkedList()
>>> l.add(1)
>>> l.add(2)
>>> l.add(3)
>>> l
[Head: 3]-> [2]-> [Tail: 1] # output
>>>
JS
// class LinkedList and its methods are presumed to exist
repr () {
let nodes = "";
let current = this.head;
while (current) {
if (current === this.head) {
nodes = `Head: ${current.data}-> `;
} else if (current.nextNode === null) {
nodes = `Tail: ${current.data}`;
} else {
nodes = `${current.data}-> `;
}
current = current.nextNode;
}
return nodes;
// running the script
let l = LinkedList();
l.add(1);
l.add(2);
l.add(3);
let result = l.repr();
console.log(result); // Head: 3-> 2-> Tail: 1
同樣,這兩個片段只會在鏈表演算法的完整實作中運行,但它們確實有效。
Attempts I have made: I tried to use JS toString(), append() and appendChild(), but they were too difficult for me to understand how best to use them, particularly as the last two modify the DOM. I'm sure there is a better way of implementing a JS equivalent of the Python __repr__(); I would like to know how it might be done.
uj5u.com熱心網友回復:
更接近的實作將使用一種toString方法。當需要轉換為字串時,會隱式呼叫此方法。Python 實際上有兩種方法,它們的目的略有不同:__repr__和__str__. JavaScript 中沒有這樣的區別。
此外,我們應該意識到 Pythonprint會隱式呼叫__repr__,這不是console.log作業原理。因此,console.log您必須強制轉換為字串。
以下是給定 Python 代碼的最字面翻譯方式(我添加了運行腳本所需的類):
class Node {
constructor(data, next=null) {
this.data = data;
this.next_node = next;
}
}
class LinkedList {
constructor() {
this.head = null;
}
add(data) {
this.head = new Node(data, this.head);
}
toString() {
let nodes = [];
let current = this.head;
while (current) {
if (current === this.head) {
nodes.push(`[Head: ${current.data}]`);
} else if (current.next_node === null) {
nodes.push(`[Tail: ${current.data}]`);
} else {
nodes.push(`[${current.data}]`);
}
current = current.next_node;
}
return nodes.join('-> ');
}
}
// running script
let l = new LinkedList();
l.add(1);
l.add(2);
l.add(3);
// Force conversion to string
console.log(`${l}`); // [Head: 3]-> [2]-> [Tail: 1]
就個人而言,我會進行以下更改(未反映在 Python 版本中):
- Produce output without the words "Head" and "Tail" and other "decoration". This is too verbose to my liking. Just output the separated values.
- Make list instances iterable, implementing the
Symbol.iteratormethod (In Python:__iter__). Then use this for implementing thetoStringmethod. - Allow the list constructor to take any number of values with which the list should be populated.
This leads to the following version:
class Node {
constructor(data, next=null) {
this.data = data;
this.next = next;
}
}
class LinkedList {
constructor(...values) { // Accept any number of values
this.head = null;
// Populate in reverse order
for (let data of values.reverse()) this.add(data);
}
add(data) {
this.head = new Node(data, this.head);
}
// Make lists iterable
*[Symbol.iterator]() {
let current = this.head;
while (current) {
yield current.data;
current = current.next;
}
}
toString() {
// Array.from triggers the above method
return Array.from(this).join("→");
}
}
// Provide the desired values immediately:
let l = new LinkedList(3, 2, 1);
console.log(`${l}`); // 3→2→1
轉載請註明出處,本文鏈接:https://www.uj5u.com/caozuo/446406.html
標籤:javascript python algorithm singly-linked-list
下一篇:操縱n對演算法的O有任何影響嗎?
