Kotlin-2.1-類和繼承
Kotlin-2.1-Classes and Inheritance
標籤:Kotlin
本節介紹了Kotlin中類和繼承的內容。類中包含首要構造器和次要構造器,還有類成員:屬性(Java中成員變數)和函式(Java中方法)。繼承主要講解的是如何過載父類的方法和屬性以及如何呼叫父類的實現。最後歸納總結過載的原則。
1-類和繼承
1-類
在Kotlin中類使用關鍵字class
宣告:
Classes in Kotlin are declared using the keyword class
:
class Invoice {
}
類宣告由類名,類頭和類主體
class Empty
1-構造器/建構函式
在Kotlin中的類可以有一個首要建構函式(primary constructor)和一個或者多個次要建構函式(secondary constructors)。首要建構函式是類頭的一部分:它跟在類名的後面並擁有可選的型別引數,如下:
class Person constructor(firstName: String) {
}
如果首要構造器沒有任何註解
或者可見性修飾符
,該constructor
class Person(firstName: String) {
}
可見性修飾符:類似於java中的public,private等修飾符。
首要構造器
不包含任何程式碼。初始化程式碼
被放置在initializer blocks
初始化程式碼塊中, 該程式碼塊以關鍵字init
作為字首。
在一個例項初始化的期間,初始化程式碼塊
以它們在類主體中出現的相同順序,順序執行
。它們可以和屬性初始化
縱橫交錯:
class InitOrderDemo(name: String) {
//屬性初始化
val firstProperty = "First property: $name" .also(::println)
//第一段初始化程式碼塊
init {
println("First initializer block that prints ${name}")
}
//屬性初始化
val secondProperty = "Second property: ${name.length}".also(::println)
//第二段初始化程式碼塊
init {
println("Second initializer block that prints ${name.length}")
}
}
fun main(args: Array<String>) {
InitOrderDemo("hello")
}
注意:首要構造器的引數可以被初始化程式碼塊所使用。它們也可以被在類主體中宣告的屬性初始化所使用:
class Customer(name: String) {
val customerKey = name.toUpperCase()
}
事實上,為了在首要構造器中宣告屬性並初始化屬性,Kotlin有一種簡潔語法:
class Person(val firstName: String, val lastName: String, var age: Int) {
// ...
}
和正常屬性非常一樣的方法,在首要構造器中的屬性可以使可變的 (var
)或者只讀的 (val
)。
如果構造器有註解或者可見性修飾符,關鍵字constructor
就是必須的,並且修飾符需要在該關鍵字之前:
class Customer public @Inject constructor(name: String) { ... }
更多細節,參考Visibility Modifiers
(可見性修飾符)。
2-次要構造器
類也可以宣告次要構造器
,次要構造器以constructor
作為字首:
class Person {
constructor(parent: Person) {
parent.children.add(this)
}
}
如果類有首要構造器,每個次要構造器都需要去代理首要構造器,直接代理或間接通過另一個次要構造器去代理。代理同類的另一個構造器,需要使用關鍵字this
:
class Person(val name: String) {
constructor(name: String, parent: Person) : this(name) {
parent.children.add(this)
}
}
注意:在初始化程式碼塊的程式碼高效地成為首要構造器的一部分。首要構造器的代理會作為次要構造器的第一行語句執行,所以在所有初始化程式碼塊的程式碼都在次要構造器之前執行。甚至,如果類沒有首要構造器,代理都會隱式地發生,初始化程式碼塊依舊會執行:
class Constructors {
init {
println("Init block")
}
constructor(i: Int) { //次要構造器,在沒有首要構造器時,依然先執行了init程式碼塊內容。
println("Constructor")
}
}
fun main(args: Array<String>) {
Constructors(1)
}
執行結果:
Init block
Constructor
如果,一個非抽象類沒有宣告任何構造器(包括首要和次要),類仍然會生成一個沒有引數的首要構造器。該構造器的可見性是public
、如果你不想你的類有一個public
構造器,你需要宣告一個空的首要構造器,並使用非預設可見性修飾符:
class DontCreateMe private constructor () {
}
注意: 在JVM中,如果首要構造器的所有引數都有預設數值,編譯器將會生成一個額外的無引數的構造器,該構造器會使用預設數值。這樣使得更容易在Kotlin中使用庫,例如Jackson或者JPA(通過無引數構造器建立類的例項)
class Customer(val customerName: String = "")
3-建立類的例項
為了建立類的例項,我們將如呼叫普通函式一樣呼叫構造器:
val invoice = Invoice() //構造器,和普通函式一樣
val customer = Customer("Joe Smith")
注意Kotlin中不使用關鍵字new
。
巢狀類、內部類、匿名內部類的建立在Nested classes
巢狀類中進行介紹。
4-類成員
類可以包含:
- 構造器和初始化程式碼塊
- 函式
- 屬性
- 巢狀和內部類
- 物件宣告
2-繼承
在Kotlin中所有類都有一個共同的超類Any
, 該超類是預設的,不需要超類的宣告:
class Example // 隱式繼承自Any
Any
不是java.lang.Object
;特別地,它除了equals(), hashCode() and toString()
沒有其他任何成員。請參考Java interoperability(Java互通性)章節。
為了宣告一個顯式的超類,我們將型別放置在類頭後的冒號後面:
open class Base(p: Int)
class Derived(p: Int) : Base(p)
如果類(子類
)有首要構造器,這個基本型別(超類
)必須在這裡被初始化,通過使用首要構造器的引數。
如果類(子類
)沒有首要構造器,每個次要構造器必須使用關鍵字super初始化基本型別(超類
),或者代理給另一個完成該任務的構造器。注意,在這種情況下,不同的次要構造器可以呼叫基本型別(超類
)的不同的構造器:
//沒有首要構造器,只有次要構造器
class MyView : View {
constructor(ctx: Context) : super(ctx) //MyView的次要構造器初始化父類,通過使用View的super(ctx)構造器。
constructor(ctx: Context, attrs: AttributeSet) : super(ctx, attrs) //MyView使用了View的另一種構造器
}
open
註解在類中是與java
中的final
相反的內容:open
允許其他類繼承自該類。預設的,在Kotlin中所有的類都是final
,這對應於Effective Java
, Item 17: Design and document for inheritance or else prohibit it.(繼承的設計和文件,否則禁止它.-不知道如何翻譯,很不通順。)
補充:本人親測,在Kotlin中所有類預設都是無法被繼承的,因為預設是
final
的。只有用open
修飾的類才可以被繼承。
1-過載方法
正如我們之前提到的,我們堅持在Kotlin中讓事情都是顯式的。不像Java,Kotlin對於覆蓋的成員(這些成員需要有open
修飾符)需要顯式的註釋:
open class Base {
open fun v() {} //open修飾
fun nv() {}
}
class Derived() : Base() {
override fun v() {} //顯式覆蓋
}
override
註解需要修飾 Derived.v()
. 如果該註解遺漏,編譯器就會報錯。如果一個函式沒有open
註解,類似Base.nv(), 在子類中宣告相同簽名的方法就是非法的,無論是否有overide
。在一個final
類中(即,一個沒有open
註解的類), 禁止擁有open
的成員(open
修飾符無效).
被overide
標記的成員其本身就是open
的,即,該成員可以在子類被過載。如果你想禁止“再過載”(過載父類的方法繼續被子類過載),可以使用final
關鍵字:
open class AnotherDerived() : Base() {
final override fun v() {} //不會繼續被子類過載。
}
2-過載屬性
過載屬性和過載方法的工作方式類似;在超類宣告的屬性在派生類中被再次宣告,必須附加上override
修飾符,此外兩個屬性必須要有相容的型別。每個宣告的屬性可以被具有初始化值得屬性過載,或者可以被具有getter方法的屬性過載。
open class Foo {
open val x: Int get() { ... }
}
class Bar1 : Foo() {
override val x: Int = ...
}
你也可以使用var
屬性過載val
的屬性,反之不可以。因為val
屬性本質具有getter
方法,將其過載為var
屬性,會在派生類中額外宣告一個setter
即可。
注意,你可以使用override
關鍵字作為首要構造器
中屬性宣告的一部分。
interface Foo {
val count: Int
}
class Bar1(override val count: Int) : Foo //屬性宣告中進行過載
class Bar2 : Foo {
override var count: Int = 0
}
3-呼叫超類的實現
在派生類中的程式碼可以呼叫其超類的函式和屬性訪問器的實現,通過使用super
關鍵字來達到這效果:
open class Foo {
open fun f() { println("Foo.f()") }
open val x: Int get() = 1
}
class Bar : Foo() {
override fun f() {
super.f() //超類中的函式
println("Bar.f()")
}
override val x: Int get() = super.x + 1 //屬性在超類中的getter
}
在內部類中,訪問外部類的超類需要使用super
關鍵字,並配合外部類的名字: [email protected]
例如([email protected]):
class Bar : Foo() {
override fun f() { /* ... */ }
override val x: Int get() = 0
inner class Baz {
fun g() {
super@Bar.f() // 呼叫外部類Bar的超類Foo的f()的實現
println(super@Bar.x) // 使用外部類Bar的超類Foo的x的getter
}
}
}
4-過載原則
Kotlin中, 繼被下列規則所規範: 如果一個類繼承了很多直接超類的同名成員,必須要顯式提供自己的實現(比如類實現了兩個介面,裡面都有同名方法function(),則一定要顯式提供實現). 為了表示呼叫的超類的實現具體是哪個超類的,我們使用super<超類名>
來指明:
open class A {
open fun f() { print("A") }
fun a() { print("a") }
}
interface B {
fun f() { print("B") } // 介面成員預設是`open`的
fun b() { print("b") }
}
class C() : A(), B {
//f()必須要被過載:
override fun f() {
super<A>.f() // 呼叫A的f()
super<B>.f() // 呼叫B的f()
}
}
a()
和 b()
兩個方法是沒有爭議的,不需要過載。方法f()
需要提供實現來消除模稜兩可的境地。
3-抽象類-Abstract
一個類和其本身的成員可以用abstract
宣告。抽象成員不能有具體實現。此外,我們不需要用open
來註釋抽象類或者抽象方法——這是預設的。
我們可以用抽象成員去過載非抽象的open成員:
open class Base {
open fun f() {}
}
abstract class Derived : Base() {
override abstract fun f() //用抽象方法過載了非抽象方法
}
4-伴侶物件
Kotlin中,不像Java或者C#,類沒有靜態方法。在大多是情況下,建議用包級別的函式。
如果你需要寫一個函式(類似static方法),該函式不需要類的例項就可以呼叫,你可以在類中給該成員新增object
宣告。
甚至更特別的情況,如果你在類中宣告一個companion
物件。你可以和Java/C#一樣通過類名作為修飾符就可以呼叫其所有成員。
2-Classes and Inheritance(原文)
1-Classes
Classes in Kotlin are declared using the keyword class
:
class Invoice {
}
The class declaration consists of the class name, the class header (specifying its type parameters, the primary constructor etc.) and the class body, surrounded by curly braces. Both the header and the body are optional; if the class has no body, curly braces can be omitted.
class Empty
1-Constructors
A class in Kotlin can have a primary constructor and one or more secondary constructors. The primary constructor is part of the class header: it goes after the class name (and optional type parameters).
class Person constructor(firstName: String) {
}
If the primary constructor does not have any annotations or visibility modifiers, the constructor
keyword can be omitted:
class Person(firstName: String) {
}
The primary constructor cannot contain any code. Initialization code can be placed in initializer blocks
, which are prefixed with the init
keyword.
During an instance initialization, the initializer blocks are executed in the same order as they appear in the class body, interleaved with the property initializers:
//sampleStart
class InitOrderDemo(name: String) {
val firstProperty = "First property: $name".also(::println)
init {
println("First initializer block that prints ${name}")
}
val secondProperty = "Second property: ${name.length}".also(::println)
init {
println("Second initializer block that prints ${name.length}")
}
}
//sampleEnd
fun main(args: Array<String>) {
InitOrderDemo("hello")
}
Note that parameters of the primary constructor can be used in the initializer blocks. They can also be used in property initializers declared in the class body:
class Customer(name: String) {
val customerKey = name.toUpperCase()
}
In fact, for declaring properties and initializing them from the primary constructor, Kotlin has a concise syntax:
class Person(val firstName: String, val lastName: String, var age: Int) {
// ...
}
Much the same way as regular properties, the properties declared in the primary constructor can be mutable (var
) or read-only (val
).
If the constructor has annotations or visibility modifiers, the constructor keyword is required, and the modifiers go before it:
class Customer public @Inject constructor(name: String) { ... }
For more details, see Visibility Modifiers
.
2-Secondary Constructors
The class can also declare secondary constructors, which are prefixed with constructor:
class Person {
constructor(parent: Person) {
parent.children.add(this)
}
}
If the class has a primary constructor, each secondary constructor needs to delegate to the primary constructor, either directly or indirectly through another secondary constructor(s). Delegation to another constructor of the same class is done using the this keyword:
class Person(val name: String) {
constructor(name: String, parent: Person) : this(name) {
parent.children.add(this)
}
}
Note that code in initializer blocks effectively becomes part of the primary constructor. Delegation to the primary constructor happens as the first statement of a secondary constructor, so the code in all initializer blocks is executed before the secondary constructor body. Even if the class has no primary constructor, the delegation still happens implicitly, and the initializer blocks are still executed:
//sampleStart
class Constructors {
init {
println("Init block")
}
constructor(i: Int) {
println("Constructor")
}
}
//sampleEnd
fun main(args: Array<String>) {
Constructors(1)
}
If a non-abstract class does not declare any constructors (primary or secondary), it will have a generated primary constructor with no arguments. The visibility of the constructor will be public. If you do not want your class to have a public constructor, you need to declare an empty primary constructor with non-default visibility:
class DontCreateMe private constructor () {
}
NOTE: On the JVM, if all of the parameters of the primary constructor have default values, the compiler will generate an additional parameterless constructor which will use the default values. This makes it easier to use Kotlin with libraries such as Jackson or JPA that create class instances through parameterless constructors.
class Customer(val customerName: String = "")
3-Creating instances of classes
To create an instance of a class, we call the constructor as if it were a regular function:
val invoice = Invoice()
val customer = Customer("Joe Smith")
Note that Kotlin does not have a new
keyword.
Creating instances of nested, inner and anonymous inner classes is described in Nested classes
.
4-Class Members
Classes can contain:
- Constructors and initializer blocks
- Functions
- Properties
- Nested and Inner Classes
- Object Declarations
2-Inheritance
All classes in Kotlin have a common superclass Any
, that is a default super for a class with no supertypes declared:
class Example // Implicitly inherits from Any
Any is not java.lang.Object
; in particular, it does not have any members other than equals(), hashCode() and toString()
. Please consult the Java interoperability
section for more details.
To declare an explicit supertype, we place the type after a colon in the class header:
open class Base(p: Int)
class Derived(p: Int) : Base(p)
If the class has a primary constructor, the base type can (and must) be initialized right there, using the parameters of the primary constructor.
If the class has no primary constructor, then each secondary constructor has to initialize the base type using the super
keyword, or to delegate to another constructor which does that. Note that in this case different secondary constructors can call different constructors of the base type:
class MyView : View {
constructor(ctx: Context) : super(ctx)
constructor(ctx: Context, attrs: AttributeSet) : super(ctx, attrs)
}
The open
annotation on a class is the opposite of Java’s final
: it allows others to inherit from this class. By default, all classes in Kotlin are final, which corresponds to Effective Java
, Item 17: Design and document for inheritance or else prohibit it.
1-Overriding Methods
As we mentioned before, we stick to making things explicit in Kotlin. And unlike Java, Kotlin requires explicit annotations for overridable members (we call them open) and for overrides:
open class Base {
open fun v() {}
fun nv() {}
}
class Derived() : Base() {
override fun v() {}
}
The override
annotation is required for Derived.v()
. If it were missing, the compiler would complain. If there is no open
annotation on a function, like Base.nv(), declaring a method with the same signature in a subclass is illegal, either with override
or without it. In a final class (e.g. a class with no open
annotation), open members are prohibited.
A member marked override
is itself open, i.e. it may be overridden in subclasses. If you want to prohibit re-overriding, use final
:
open class AnotherDerived() : Base() {
final override fun v() {}
}
2-Overriding Properties
Overriding properties works in a similar way to overriding methods; properties declared on a superclass that are then redeclared on a derived class must be prefaced with override
, and they must have a compatible type. Each declared property can be overridden by a property with an initializer or by a property with a getter method.
open class Foo {
open val x: Int get() { ... }
}
class Bar1 : Foo() {
override val x: Int = ...
}
You can also override a val
property with a var
property, but not vice versa. This is allowed because a val
property essentially declares a getter method, and overriding it as a var
additionally declares a setter method in the derived class.
Note that you can use the override
keyword as part of the property declaration in a primary constructor.
interface Foo {
val count: Int
}
class Bar1(override val count: Int) : Foo
class Bar2 : Foo {
override var count: Int = 0
}
3-Calling the superclass implementation
Code in a derived class can call its superclass functions and property accessors implementations using the super
keyword:
open class Foo {
open fun f() { println("Foo.f()") }
open val x: Int get() = 1
}
class Bar : Foo() {
override fun f() {
super.f()
println("Bar.f()")
}
override val x: Int get() = super.x + 1
}
Inside an inner class, accessing the superclass of the outer class is done with the super keyword qualified with the outer class name: [email protected]
:
class Bar : Foo() {
override fun f() { /* ... */ }
override val x: Int get() = 0
inner class Baz {
fun g() {
super@Bar.f() // Calls Foo's implementation of f()
println(super@Bar.x) // Uses Foo's implementation of x's getter
}
}
}
4-Overriding Rules
In Kotlin, implementation inheritance is regulated by the following rule: if a class inherits many implementations of the same member from its immediate superclasses, it must override this member and provide its own implementation (perhaps, using one of the inherited ones). To denote the supertype from which the inherited implementation is taken, we use super
qualified by the supertype name in angle brackets, e.g. super<Base>
:
open class A {
open fun f() { print("A") }
fun a() { print("a") }
}
interface B {
fun f() { print("B") } // interface members are 'open' by default
fun b() { print("b") }
}
class C() : A(), B {
// The compiler requires f() to be overridden:
override fun f() {
super<A>.f() // call to A.f()
super<B>.f() // call to B.f()
}
}
It’s fine to inherit from both A
and B
, and we have no problems with a()
and b()
since C
inherits only one implementation of each of these functions. But for f()
we have two implementations inherited by C
, and thus we have to override f()
in C
and provide our own implementation that eliminates the ambiguity.
3-Abstract Classes
A class and some of its members may be declared abstract
. An abstract member does not have an implementation in its class. Note that we do not need to annotate an abstract class or function with open – it goes without saying.
We can override a non-abstract open member with an abstract one
open class Base {
open fun f() {}
}
abstract class Derived : Base() {
override abstract fun f()
}
4-Companion Objects
In Kotlin, unlike Java or C#, classes do not have static methods. In most cases, it’s recommended to simply use package-level functions instead.
If you need to write a function that can be called without having a class instance but needs access to the internals of a class (for example, a factory method), you can write it as a member of an object declaration
inside that class.
Even more specifically, if you declare a companion object
inside your class, you’ll be able to call its members with the same syntax as calling static methods in Java/C#, using only the class name as a qualifier.
相關推薦
Kotlin-2.1-類和繼承
Kotlin-2.1-Classes and Inheritance 標籤:Kotlin 本節介紹了Kotlin中類和繼承的內容。類中包含首要構造器和次要構造器,還有類成員:屬性(Java中成員變數)和函式(Java中方法)。繼承主要講解的是如何過載
重溫Java經典教程(The Java™ Tutorials)第三篇-Java語言-第二章-2.1類和物件
巢狀類 巢狀類幾種型別 The Java programming language allows you to define a class within another class. Such a class is called a nested class and
(1)Object類 (2)包裝類和數學處理類 (3)String類
lean 由於 哈希 出現 接口類 HA 支持 indexof 類的成員 1.Object類1.1 基本概念 java.lang.Object類是Java類層次結構的根類,任何類都是Object類的直接/間接子類。 1.2 常用的方法(重點) Object() -
(1)String類 (2)StringBuilder類和StringBuffer類 (3)日期相關的類
ins 查找 regex string類 a-z 當前 依次 AS 下標 1.String類(重中之重)1.1 常用的方法(練熟、記住)(1)常用的構造方法 String() - 使用無參的方式構造空字符串對象。 String(byte[] bytes) - 根據參
3.0 類的內建方法 3.1 類的繼承(1) 3.2 類的繼承(2)
3.0 類的內建方法 所謂內部類,就是在類的內部定義的類,主要目的是為了更好的抽象現實世界。 比如,汽車是一個類,汽車的地盤,輪胎也可以抽象為類,將其定義到汽車的類中,則形成內部類,更好的描述汽車類,因為底盤、輪胎是汽車的一部分 建立內部類的方法和建立類的方法很相似 內部類的例項化方法 方法1:直接使用外部類
3.0 類的內建方法 3.1 類的繼承(1) 3.2 類的繼承(2)
3.0 類的內建方法 所謂內部類,就是在類的內部定義的類,主要目的是為了更好的抽象現實世界。 比如,汽車是一個類,汽車的地盤,輪胎也可以抽象為類,將其定義到汽車的類中,則形成內部類,更好的描述汽車類,因為底盤、輪胎是汽車的一部分 建立內部類的方法和建立類的方法很相似 內部類的例項化方
Kotlin 類和繼承
類宣告 Kotlin使用class關鍵字宣告類: class Foo { } 宣告分為宣告頭和宣告體。其中宣告體是可選的,如下: class Bar 建構函式 Kotlin建構函式分為主建構函式(primary constructor)和輔助
Android知識體系梳理筆記五:Kotlin學習筆記一:類和繼承以及Anko(全)的基本使用
前言 對於kotlin,我是邊寫專案邊學的方式來學習的,這些都是在做專案的時候遇到的問題及擴充套件學習的時候記錄的,雖然有些內容不會涉及,但是我認為這種邊寫程式碼邊學習的方式特別有助於記憶,畢竟紙上得來終覺淺! 類和繼承 Kotlin較Java在繼承和實現
Kotlin程式設計之父類和繼承父類
Kotlin程式設計相關知識點介紹: 1. 預設繼承Any超類: 在Kotlin程式設計中,Any類是超類. public open class Any { public o
python:類2——有關類和對象的BIF內置函數
subclass 提前 變量 類和對象 ins peer 設置 clas 需要 1、檢查、判斷 issubclass(class, classinfo)如果第一個參數是第二個參數的子類,返回true,註意: 非嚴格(自己可以認為是自己的子類); 第二個參數可以是由多個cl
《C#圖解教程》讀書筆記之四:類和繼承
intern html pan 類中訪問 ted obj 小寫 his new 本篇已收錄至《C#圖解教程》讀書筆記目錄貼,點擊訪問該目錄可獲取更多內容。 一、萬物之宗:Object (1)除了特殊的Object類,其他所有類都是派生類,即使他們沒有顯示基類定義。
三、面向對象——1-類和對象
align this -a tro str 定義 p s 面向對象 style 1-類和對象 1.定義類 2.對象的產生和使用 3.對象、引用和指針 4.this三、面向對象——1-類和對象
ts-類和繼承
world end spa nbsp moved move clas let new class Greeter { greeting: string; constructor(message: string) { this.greetin
C#圖解 類和繼承
類的方法 png gpo 派生類 引用調用 有一個 圖解 匹配 關於 ---恢復內容開始--- 一:類繼承: 派生類成員組成如下: 1:自己聲明的成員 基類的成員 2:派生類不能刪除他所繼承的任何成員 例如:展示了名為OtherClass的類的聲明,他繼承的名
(轉載)【笨木頭Lua專欄】基礎補充20:面向對象——類和繼承
笑話 ava span 生成 code BE 手機 情況 忽略 終於來了,在Lua中的面向對象編程,相信目前學習Lua的大部分人都是為了開發手機網遊吧。而且基本都是奔著腳本語言的熱更新特性去的,所以全腳本開發變得十分流行。 對於普及不太廣的Lua(相對於C++、Java等主
子類和繼承
局部變量 不能 訪問權限 abs bstr 允許 fin 構造 個數 任何類都是Object類(java.lang包中的類)的子孫類。 子類和父類在同一個包中:不繼承private成員變量和private方法。 子類和父類不在同一個包中:不繼承private和友好訪問權限
How Javascript works (Javascript工作原理) (十五) 類和繼承及 Babel 和 TypeScript 代碼轉換探秘
屬性集 重寫 details 函數調用 有趣的 feature 性能優化 mage 轉化 個人總結:讀完這篇文章需要15分鐘,文章主要講解了Babel和TypeScript的工作原理,(例如對es6 類的轉換,是將原始es6代碼轉換為es5代碼,這些代碼中包含著類似於 _c
在CDH上用外部Spark2.2.1安裝和配置 CarbonData
表示 相關 iyu top arch slaves path 中央倉庫 tar -zcvf 在CDH上用外部Spark2.2.1 (hadoop free版本)standalone 模式安裝和配置 CarbonData ===================
類和繼承
代碼 ret 包含 protect 轉換成 intern mas obj int 所有的類都派生自Object; 派生類引用可以轉換成基類; 屏蔽基類成員使用關鍵字new則可以屏蔽基類成員; 虛方法和覆寫方法 基類的方法被標記為virtual 在派生類中有匹配的ove
菜鳥的C++ 知識盲區(跌倒)到知識黑洞(放棄)---------2.1變數和基本型別
前言 說來話長,本人是一個不合格的程式設計師,最起碼我覺得我水平很菜。本科就讀於北方一個沒落的211,學的是機械設計製造及其自動化,基本上本科沒有接觸過什麼“高深”的關於程式設計的專案,不過稀裡糊塗計算機二級考過了,但是C語言並沒有學的很好,什麼指標啦只是大概知道。本科