Summary of Android Interview Techniques

I have always been afraid to write about interview content, fearing that many people think that as long as they memorize enough interview questions, they can easily get into BAT. I hope that everyone does not think that rote memorization of interview questions can yield anything; more importantly, it should be about understanding, reflection, and summarizing one’s strengths and weaknesses.

MVC, MVP, and MVVM

1. View sends commands to Controller. 2. Controller organizes communication between different layers and controls the flow of the application. It handles events and responds. “Events” include user actions and changes in the data Model. 3. Model sends new data to View, giving users feedback. All communication is unidirectional.

Summary of Android Interview Techniques

  • MVP communication method: 1. Communication between parts is bidirectional. 2. View and Model do not communicate directly, but pass through Presenter. 3. View is very thin, does not deploy any business logic, called “Passive View”, meaning it has no initiative, while Presenter is very thick, all logic is deployed there.

Summary of Android Interview TechniquesMVVM model is an upgrade of MVP: it is basically identical to MVP. The only difference is that it uses two-way binding: changes in the View are automatically reflected in the ViewModel, and vice versa.

Summary of Android Interview Techniques(The above content is taken from: http://www.ruanyifeng.com/blog/2015/02/mvcmvp_mvvm.html)

We can understand the data structures and related classes we establish for the business model as the Model of an Android App. The Model is unrelated to the View but related to business, for example, reading data from a database should belong to the model layer. (Thanks to @Xander for the explanation) My guess:

As for why we usually write database data reading directly in Activity, my guess is that it is simple. Imagine if we want to standardize, we first define an interface getDataFromDB(), then write a class to implement the getDataFromDB() method. If we later change the method used to request data, we can directly rewrite the implementation class. It sounds good, but is it really meaningful to add at least two class files just to read some data from the database? Of course, network requests belong to the business logic layer C layer.

Disk Cache of Volley

During the interview, we talked about the data cache from network requests using Volley. At that time, it was mentioned that Volley would write each piece of data requested through the network to a local file using FileOutputStream. So the question arises: this cache file is declared in a folder on the SD card (it can also be getCacheFile()). If network data requests keep coming, this cache folder will grow indefinitely, and when it reaches the SD card’s capacity, an exception will occur (because the storage space is full). This problem I really hadn’t thought of before, and I couldn’t explain it at the time. After I got home, I quickly looked at the code and found out that Volley had considered this issue (sweat! Thinking about it now). Looking through the code DiskBasedCache#pruneIfNeeded()

Summary of Android Interview Techniques

Among them,mMaxCacheSizeInBytes is a size of the cache folder passed in the constructor. If not passed, the default is 5MB.

Through this method, we can see that every time it is called, a neededSpace is passed in, which is the disk size needed (i.e., the size required for the new cached file). It first checks whether this neededSpace can be successfully applied for and whether it will exceed the maximum available capacity. If it exceeds, it traverses the headers of the locally saved cache files (the header contains the cache expiration time, occupied size, etc.) to delete files until the available capacity is no longer greater than the declared size of the cache folder. Among them, HYSTERESIS_FACTOR is a constant value of 0.9, which is probably to prevent errors.

Calculation of Volley Cache File Names

This is a question I’ve never understood. The code is as follows:

Summary of Android Interview Techniques

Why do we need to split a key into two parts, calculate hashCode separately, and then concatenate them?

I previously asked this question on stackoverflow #link. Forgive me, I initially did not understand others’ answers. Until recently, when I was asked how to design a HashMap to avoid value overwriting, I thought of the reason. First, let’s look at the implementation of String#hashCode():

Summary of Android Interview Techniques

From the implementation above, we can see that the hashcode of a String is calculated based on the int value of each letter in the character array plus the previous hash value multiplied by 31. As for why it is 31, I am not sure.

However, it can be confirmed that hashcode is not unique. If you don’t believe it, run the following two outputs:

Summary of Android Interview Techniques

These two strings are derived from the hashcode algorithm, and their hashcodes are both 12345. Please see the reverse algorithm here.

Returning to our question, why do we need to split a key into two parts? Now it can be confidently answered that the purpose is to avoid filename duplication caused by hashcode repetition as much as possible (the probability of two hashes being repeated is certainly smaller than that of one repetition, right?). By the way, the small probability does not mean that it does not exist. However, the speed of calculating hashcode in Java is very fast, which should be a trade-off between efficiency and security.

Underlying Implementation of HashMap

HashMap is implemented internally through an array, and each position in the array is an object of Entry, which is actually a node of a linked list. Ah, I remember we talked about data structures in college, but I forgot all about it. According to the hash algorithm, find out which index the current key should be stored in the array. If there is already a value, it will be stored in the next position of the linked list at the index of Entry. Referring to how to implement HashMap to prevent value overwriting, as mentioned in Volley.

Differences Between Atomic, volatile, and synchronized

When I encountered this problem in Java basics, I was asked if i++ could be replaced with volatile and synchronized. At that time, I didn’t know, but I felt that volatile would cause the variable to be incremented halfway when a thread switch occurs. Looking back, I was right. volatile can ensure that when a variable is modified in one thread, its value can immediately reflect back to the main memory, ensuring that all threads see the value of this variable consistently. However, there is a premise: it does not have atomicity of operations, which means it is not suitable when the write operation to that variable depends on the variable itself. For example, i++, i+=1; this is not suitable. However, it can be changed to num=i+1; if i is of type volatile, then num is safe. In summary, it cannot act on itself. synchronized is based on code blocks; as long as it is included in the synchronized block, it is thread-safe. Since we are talking about thread safety, let’s learn a few more: AtomicInteger, a lightweight synchronized. It does not use synchronized code blocks but uses a Lock-Free algorithm (I don’t quite understand, but looking at the code, it is a dead loop calling the underlying comparison method until it is the same before exiting the loop). The final result is that in high concurrency or intense competition, its efficiency is higher than synchronized. ThreadLocal, private data for threads. Mainly used when a thread modifies internal data without affecting other threads; note that static is needed. For a detailed analysis, see this article . Let me add one more thing I just learned. Using the clone() method, if multiple objects of a class want to share a variable inside the object without making it static, shallow copying can be used. (Refer to the prototype design pattern).

Finally: A Few Thoughts

It is a feeling, and I want to tell everyone: interviews are really annoying because the questions are random, and knowledge is infinite. Moreover, many answers do not have standards. Just like the MV* mentioned in this article, perhaps my understanding of the above is still problematic, but I believe that architecture is dead, and the most suitable is the best. However, one thing is certain: interviews are also a form of learning; at least they can let you know where your weaknesses lie. Be good at summarizing; since you know where you are lacking, if you make up for it, you will be the best.

Leave a Comment

×