Back home

SENI #028

SENI #028

SENI 028

Ini adalah pasal 28

SENI adalah kegiatan yang diprakarsai oleh 由左耳朵耗子--陈皓: Kerjakan setidaknya satu pertanyaan algoritma leetcode setiap minggu, baca dan komentari setidaknya satu artikel teknis berbahasa Inggris, pelajari setidaknya satu keterampilan teknis, dan bagikan artikel yang berisi opini dan pemikiran. (Artinya, Algoritma, Review, Tip, dan Share disebut sebagai SENI) dan bertahan setidaknya selama satu tahun.

Pertanyaan algoritma algoritma

2. Tambahkan dua angka

Kesulitan: Sedang

Diberikan dua daftar tertaut tidak kosong untuk mewakili dua bilangan bulat non-negatif. Diantaranya, masing-masing digitnya disimpan dalam urutan terbalik, dan setiap nodenya hanya dapat menyimpan satu digit.

Jika kita menambahkan dua angka ini, daftar tertaut baru akan dihasilkan yang mewakili jumlahnya.

Anda dapat berasumsi bahwa tidak ada angka yang dimulai dengan 0 kecuali angka 0.

Contoh:

输入:(2 -> 4 -> 3) + (5 -> 6 -> 4)
输出:7 -> 0 -> 8
原因:342 + 465 = 807

Tingkat kesulitan soal ini sedang. Kesulitan utama terletak pada pertimbangan kasus-kasus yang berbeda. Jawaban pertama saya adalah sebagai berikut:

Solusi

Bahasa: C


/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     struct ListNode *next;
 * };
 */
struct ListNode* addTwoNumbers(struct ListNode* l1, struct ListNode* l2) {
    
    struct ListNode* root = NULL;//(struct ListNode*)malloc(sizeof(struct ListNode));
    struct ListNode* p = NULL;
    int sum = 0;
    while (l1 != NULL || l2 != NULL ) {
        
        if (l1 != NULL && l2 != NULL ) {
            sum = l1->val + l2->val + sum / 10;
            l1 = l1->next;
            l2 = l2->next;
        }
        else if (l1 != NULL){
            sum = l1->val+ sum / 10;
            l1 = l1->next;
        }
        else if (l2 != NULL){
            sum = l2->val +  sum / 10;
            l2 = l2->next;
        }
        
        if (p == NULL) {
            p = (struct ListNode*)malloc(sizeof(struct ListNode));
            p->val =  sum % 10;
            p->next = NULL;
            root = p;
        }
        else{
            struct ListNode*  temp = (struct ListNode*)malloc(sizeof(struct ListNode));
            temp->val =  sum % 10;
            temp->next = NULL;
            
            p->next = temp;
            p=temp;
        }
    }
    
    return root;
}

Logika di atas juga sangat jelas dan sederhana, namun jika inputnya 5 atau 5, hasilnya salah. Karena saya kurang memikirkan situasinya.

Hasil akhir:

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     struct ListNode *next;
 * };
 */
struct ListNode* addTwoNumbers(struct ListNode* l1, struct ListNode* l2) {
    
    struct ListNode* root = NULL;//(struct ListNode*)malloc(sizeof(struct ListNode));
    struct ListNode* p = NULL;
    int sum = 0;
    while (l1 != NULL || l2 != NULL ) {
        
        int flag = 0;
        
        if (l1 != NULL && l2 != NULL ) {
            sum = l1->val + l2->val + sum / 10;
            l1 = l1->next;
            l2 = l2->next;
            
            if (l1 == NULL && l2 == NULL) {
                flag = 1;
            }
        }
        else if (l1 != NULL){
            sum = l1->val+ sum / 10;
            l1 = l1->next;
            
            if (l1 == NULL) {
                flag = 1;
            }
        }
        else if (l2 != NULL){
            sum = l2->val +  sum / 10;
            l2 = l2->next;
            
            if (l2 == NULL) {
                flag = 1;
            }
        }
        
        if (p == NULL) {
            p = (struct ListNode*)malloc(sizeof(struct ListNode));
            p->val =  sum % 10;
            p->next = NULL;
            root = p;
        }
        else{
            struct ListNode*  temp = (struct ListNode*)malloc(sizeof(struct ListNode));
            temp->val =  sum % 10;
            temp->next = NULL;
            
            p->next = temp;
            p=temp;
        }
        
        if (flag ==1 && sum >=10) {
            struct ListNode*  temp = (struct ListNode*)malloc(sizeof(struct ListNode));
            temp->val =  sum / 10;
            temp->next = NULL;
            
            p->next = temp;
            p=temp;
        }
    }

    return root;
}

Hasil dari operasi di atas adalah:

Runtime: 40 ms, faster than 10.93% of C online submissions for Add Two Numbers.
Memory Usage: 17.7 MB, less than 55.74% of C online submissions for Add Two Numbers.

Catatan pengiriman berikut memiliki waktu berjalan 16 md, saat ini berada di peringkat pertama:

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     struct ListNode *next;
 * };
 */
struct ListNode* recursiveAddTwoNumbers(struct ListNode* l1, struct ListNode* l2, int carry);
struct ListNode* recursiveFinishAdd(struct ListNode* l, int carry);

struct ListNode* addTwoNumbers(struct ListNode* l1, struct ListNode* l2) {
    return recursiveAddTwoNumbers(l1, l2, 0);
}

struct ListNode* recursiveAddTwoNumbers(struct ListNode* l1, struct ListNode* l2, int carry) {
    if(l1 == NULL) return recursiveFinishAdd(l2, carry);
    if(l2 == NULL) return recursiveFinishAdd(l1, carry);
    
    int val = l1->val + l2->val + carry;
    struct ListNode *next = recursiveAddTwoNumbers(l1->next, l2->next, val/10);
    
    struct ListNode *node = malloc(sizeof(struct ListNode));
    node->val = val%10;
    node->next = next;
    
    return node;
}

struct ListNode* recursiveFinishAdd(struct ListNode* l, int carry) {
    if(l == NULL) {
        if(carry == 0) return NULL;
        struct ListNode *node = malloc(sizeof(struct ListNode));
        node->val = carry;
        node->next = NULL;
        return node;
    }
    
    int val = l->val + carry;
    struct ListNode *next = recursiveFinishAdd(l->next, val/10);
    
    struct ListNode *node = malloc(sizeof(struct ListNode));
    node->val = val%10;
    node->next = next;
    
    return node;
}

Tapi saya menjalankannya dan hasilnya adalah sebagai berikut, sehingga lingkungan pengujian juga berubah, dan waktu berjalan dari kode yang sama juga berubah.

Runtime: 32 ms, faster than 46.07% of C online submissions for Add Two Numbers.
Memory Usage: 18.2 MB, less than 5.07% of C online submissions for Add Two Numbers.

3. Substring terpanjang tanpa karakter berulang Salin untuk Penurunan Harga

Kesulitan: Sedang

Diberikan sebuah string, silakan cari panjang substring terpanjang yang tidak mengandung karakter berulang.

Contoh 1:

输入: "abcabcbb"
输出: 3 
解释: 因为无重复字符的最长子串是 "abc",所以其长度为 3。

Contoh 2:

输入: "bbbbb"
输出: 1
解释: 因为无重复字符的最长子串是 "b",所以其长度为 1。

Contoh 3:

输入: "pwwkew"
输出: 3
解释: 因为无重复字符的最长子串是 "wke",所以其长度为 3。
     请注意,你的答案必须是 子串 的长度,"pwke" 是一个子序列,不是子串。

Solusi

Bahasa: C

Jawaban saya adalah sebagai berikut:

//滑动窗口
int lengthOfLongestSubstring(char* s) {
    int maxLength = 0;
    int strLength = strlen(s);
    int leftP = 0;
    int sublength = 0;
    for(int i = 0; i < strLength; i++){
        int flag = 0;
        for(int j = leftP; j < i; j++){
            if (s[j]== s[i]) {
                flag =1;
                leftP = j+1;
                sublength = i - j;
                break;
            }
        }
        
        if (flag ==0){
            sublength++;
        }

        if(sublength > maxLength) {
            maxLength = sublength;
        }
    }
    if(sublength > maxLength) {
        maxLength = sublength;
    }
  
    return maxLength;
}

Berikut ini adalah contoh yang membutuhkan waktu 8 ms untuk dieksekusi, tetapi saya menjalankannya dan waktu eksekusinya sama dengan kode saya (berikut ini adalah waktu eksekusi kode saya)

int lengthOfLongestSubstring(char* s) {
int maxlen = 0,currlen = 0;
    int table[128], i, j, start = 0;
    memset(table, 0, sizeof(table));
    for (i = 0; s[i] != '\0'; ++i){
        int num =  ++table[s[i]];
        if( num == 2 ){
            if (currlen > maxlen){
                maxlen = currlen;
            }
            for(j = start; j < i; ++j){
                if (s[j] == s[i]){
                    table[s[j]] = 1;
                    start = j+1;
                    break;
                }else{
                    --currlen;
                    table[s[j]] = 0;
                }
            }
        }else{
            ++currlen;
        }
    }
    if (currlen > maxlen){
        maxlen = currlen;
    }

    return maxlen;
}

Versi bahasa Inggris: contoh pengiriman 8 ms, ide implementasi ini adalah

int lengthOfLongestSubstring(char* s)
{
    int len=0;
    char *end=s,*temp;
    char* addressTable[128]={NULL};
    while(*end){
        temp = addressTable[*end];
        addressTable[*end]=end;
        if(temp>=s){
            len=end-s>len?end-s:len;
            s = temp+1;
        }
        end++;
    }
    len=end-s>len?end-s:len;
    return len;
}

4. Temukan median dari dua larik terurut

Kesulitan: Kesulitan

Diberikan dua array terurut nums1 dan nums2 berukuran m dan n.

Temukan median dari dua larik terurut ini, dan kompleksitas waktu dari algoritme harus O(log(m + n)).

Anda dapat berasumsi bahwa nums1 dan nums2 tidak akan kosong secara bersamaan.

Contoh 1:

nums1 = [1, 3]
nums2 = [2]

则中位数是 2.0

Contoh 2:

nums1 = [1, 2]
nums2 = [3, 4]

则中位数是 (2 + 3)/2 = 2.5

Solusi

Bahasa: C

Gabungkan array terlebih dahulu, lalu hitung

double findMedianSortedArrays(int* nums1, int nums1Size, int* nums2, int nums2Size) {

    int sumSize = nums1Size + nums2Size;
    int *sum =   (int*)malloc(sizeof(int) * sumSize);
    int loop1 = 0;
    int loop2 = 0;
    for (int i =0; i< sumSize; i++) {//合并数组
        if (loop1>=nums1Size) {
            for (int j = i; j < sumSize; j++) {
                sum[j] = nums2[loop2++];
            }
            break;
        }

        if (loop2>=nums2Size) {
            for (int j = i; j < sumSize; j++) {
                sum[j] = nums1[loop1++];
            }
            break;
        }

        int r1 = nums1[loop1];
        int r2 = nums2[loop2];
        if (r1 < r2) {
            sum[i] = r1;
            loop1++;
        }
        else{
           sum[i] = r2;
            loop2++;
        }

    }

    //计算最终结果
    double r = 0;
    if (sumSize  % 2 == 0 ) {
        int l1 = sumSize  / 2;
        int l2 = l1 - 1;

        r = ((double)(sum[l1] + sum[l2]))/2;
    }
    else{
        int l =  sumSize  / 2;
        r = sum[l];
    }

    return r;
}

Ulasan

Artikel ini terutama membahas tentang apa musuh sebenarnya Anda ketika memulai bisnis dan membuat produk. https://dandan2009.github.io/2019/03/20/competitors-are-not-the-enemy/

Kiat

Saat git mengirimkan kode, terdapat informasi penulis, seperti nama pengguna dan alamat email. Namun, jika informasi penulis salah secara tidak sengaja atau tidak sesuai dengan spesifikasi, bagaimana cara memodifikasinya? Skrip berikut dapat membantu Anda mengubah informasi penulis yang dikirimkan. Perhatikan bahwa di sini adalah semua informasi penulis yang dikirimkan yang telah dimodifikasi. Saat menggunakannya, berhati-hatilah untuk tidak mengubah kiriman orang lain menjadi kiriman Anda.


#!/bin/sh

git filter-branch --env-filter '

an="$GIT_AUTHOR_NAME"
am="$GIT_AUTHOR_EMAIL"
cn="$GIT_COMMITTER_NAME"
cm="$GIT_COMMITTER_EMAIL"
if [ "$GIT_COMMITTER_EMAIL" = "要修改的@邮箱地址.com" ]
then
    cn="想要改成的用户名"
    cm="想要改成的邮箱"
fi
if [ "$GIT_AUTHOR_EMAIL" = "要修改的@邮箱地址.com" ]
then
    an="想要改成的用户名"
    am="想要改成的邮箱"
fi
    export GIT_AUTHOR_NAME="$an"
    export GIT_AUTHOR_EMAIL="$am"
    export GIT_COMMITTER_NAME="$cn"
    export GIT_COMMITTER_EMAIL="$cm"
'

Setelah langkah-langkah di atas dijalankan, masukkan riwayat yang benar ke Github:

git push --force --tags origin 'refs/heads/*'

Catatan: 1 Harap buat cadangan kode sebelum mengeksekusi 2 Setelah menjalankan git push --force --tags origin 'refs/heads/*', hapus gudang lokal yang ada dan kloning lagi.

Saat Anda menjalankan kembali skrip di atas di gudang yang sama, Anda akan diminta:

Cannot create a new backup.
A previous backup already exists in refs/original/
Force overwriting the backup with -f

Jalankan saja perintah berikut

git update-ref -d refs/original/refs/heads/master

Bagikan

Konten berikut dibagikan oleh seorang netizen di grup WeChat.

Kasus ini sangat sederhana dan menarik, namun permintaannya nyata dan kuat. Berbagi dari penulis asli telah memberi kami banyak inspirasi untuk penemuan titik nyeri dan pengembangan produk. Situasi dasar

  1. Nama Produk: Perangkat Lunak Salem
  2. Fitur produk: Aplikasi iOS Alkitab versi Spanyol
  3. Volume instalasi: lebih dari 1,3 juta
  4. Pendapatan bulanan: lebih dari $10.000 4 inspirasi yang dibawakan oleh produk dari 0 hingga 1
  1. Penulis memahami bahasa Spanyol, jadi dia membuat Alkitab versi bahasa Spanyol sebagai aplikasi Jos, dan versi audio bahasa Spanyol dari aplikasi tersebut dirilis setelah jangka waktu tertentu.
  1. Dia menyebutkan cara untuk menemukan kebutuhan nyata dengan cepat: menelusuri daftar App Store, mencari aplikasi dengan ulasan buruk dari atas ke bawah, lalu menyalinnya ke model bahasa lain. Karena kebutuhan ini telah dikonfirmasi dan modelnya berhasil, Anda hanya perlu mengubah beberapa variabel baru untuk mendapatkan keuntungan dengan cepat, seperti mengubah variabel bahasa, mengubah variabel saluran, dll.
  2. Selain membuat versi teks dari Alkitab bahasa Spanyol, penulis menyebutkan bahwa operasi kunci untuk pertumbuhan pendapatannya adalah membuat versi audio dari konten gratis ini, yang sangat meningkatkan pendapatan pasifnya. Inspirasinya bagi kami, selain variabel seperti bahasa dan saluran, bentuk media juga menjadi variabel. Teks, gambar, audio, dan video. Setiap jenis memiliki permintaan yang sesuai. Kita perlu mencari dan menemukan celah di pasar.
  3. Dari kasus ini kita juga bisa mendapatkan inspirasi: mencari karya di bidang hak cipta publik, mengolahnya kembali dan memproduksinya kembali agar lebih sesuai dengan kebutuhan masyarakat, seperti Water Margin dan Dream of Red Mansions, mengolahnya kembali dan mendistribusikannya kembali

Disebutkan di sini untuk membuat APP Anda sendiri. Jika Anda ingin berkembang secara mandiri tetapi tidak punya ide, Anda bisa mencobanya.