为了练习,我正在尝试在Scala中实现LinkedList
。
主要问题是关于Null
参考。
但首先是一些代码:
class Node(xkey: String, xnext: Option[Node], xinfo: Int) {
val key: String = xkey;
var next = xnext.getOrElse(None);
var info: Int = xinfo;
def this(xkey: String, xinfo: Int) {
this(xkey, None, xinfo);
}
def this(xkey: String) {
this(xkey, None, -1);
}
@Override
override def toString: String = key + ":" + info
}
此时,我已经开始关注事情了。
我在构造中将xnext
声明为Option[Node]
,因为此linkedList
中的尾部没有下一个。
在我的第一次尝试中,它只是一个Node
,但是有了null对象的问题,因为编译器只是告诉我“null无法转换为Node”(或类似的东西,我现在不记得了) ) - 所以我切换到这个选项。
但是,可以吗?因为,您知道,对我而言,接下来应该是Node
,而不是Option
,否则,我不知道,linkedList
如何引用下一个节点。
无论如何,第二类(即我的链接列表)
class LinkedNode {
private var first: Option[Node] = None;
private var last: Option[Node] = None;
def addNode(newNode: Node) = {
if (first == null) {
first = Some(newNode);
last = Some(newNode);
first.next = last;
}
else {
last.next = newNode;
newNode.next = null;
last = newNode
}
}
def size(): Long = {
var currentNode : = first;
var size = 0L;
while (currentNode != null) {
size+=1;
currentNode = currentNode.next;
}
size
}
def findNodeByKey(key: String) : Node = {
var currentNode = first;
while(currentNode != null) {
if (currentNode.key.equals(key))
currentNode
else {
currentNode = currentNode.next;
}
}
currentNode;
}
def delNodeByKey(key : String) : Boolean = {
var currentNode = first;
var previousNode = first;
while(currentNode != null) {
if (currentNode.key.equals(key)) {
previousNode = currentNode.next;
return true;
}
previousNode = currentNode;
currentNode = currentNode.next;
}
return false;
}
}
没什么。我已经阻止了我的构造函数因为第一个也是最后一个。
我该如何申报? Node
?或Option[Node]
?
Add
方法也存在问题
当我添加节点时,我想添加Node
对象,而不是Option[Node]
而且我无法了解如何使用所有Option
,Some
和None
类来实现我想要的内容。
我知道我的要求不应该这么模糊,但是有什么帮助吗?
P.S。我已经阅读了this Q/A但它没有帮助我
答案 0 :(得分:3)
此时,我已经开始关注事情了。我将构造中的xnext声明为Option [Node],因为此linkedList中的尾部没有下一个。 [...] 但是,好吗?因为,你知道,对我而言,接下来应该是Node,而不是Option,否则,我不知道,在linkedList中如何引用下一个Node。
这是替换null
的一个很好的解决方案,您肯定希望这样做以防止空指针异常等。 Option[Node]
只是包含在容器中的Node
(或None
)。您可以检查它是否具有isEmpty
的值,或者使用get
获取其值(如果Option为空,则会抛出异常)。
与null
的唯一区别在于,您需要检查isEmpty
是否option.get
而不是检查null,并且需要打开({1}} None
)当您确定它不是option match {
case Some(x) => println(x)
case None => println("Whoops, no value :(")
}
时,它会明确地显示。
从选项中检索值的更典型(scala-typical)方法是模式匹配:
Option[Node]
关于你的其他问题,它们确实有点模糊。
我该如何判断它们?节点?或选项[节点]?
如果存在变量没有值的可能性,请使用null
(例如,如果您有时在Java中将其设置为Option[Node]
。)
当我添加节点时,我想添加一个Node对象,而不是Option [Node]。
不,您想在内部添加Option[Node].isEmpty
,因为稍后需要检查节点是否已设置。在Scala中,与设置为null相比,最好通过addNode
执行此操作。您已经在代码的某些部分(例如Some(newNode)
)执行了此操作,您可以addNode
(我称之为"将节点包装在选项& #34;,但我不完全确定这是否是正确的术语。
我无法通过所有Option,Some和None课程获得如何实现我想要的东西。
您在null
中所做的事情在某种程度上似乎是正确的,但您却试图在else
分支中再次使用// We don't need Option[Node] for the parameter, because there
// _must_ be a Node value to be added
def addNode(newNode: Node) = {
if (first.isEmpty) {
first = Some(newNode)
last = Some(newNode)
first.next = last
} else {
newNode.next = None
last.next = Some(newNode)
last = Some(newNode)
}
}
。怎么样:
def send_commands(conn):
while True:
cmd = input()
if cmd == 'quit':
conn.close()
s.close()
sys.exit()
if len(str.encode(cmd)) > 0:
conn.send(str.encode(cmd))
client_response = str(conn.recv(1024), "utf-8")
print(client_response, end="")
(我没有运行该代码,也没有彻底检查您的逻辑)