Bạn sẽ "viết 1 hàm tìm số có giá trị lớn thứ 2 trong dãy số cho trước" như thế nào?

Khi bạn viết một hàm bạn phải đảm bảo kiểm tra hết các edge cases của nó, đó là việc bình thường. Lấy lại cái ví dụ sqrt của bạn. Trong document của C++ định nghĩa đàng hoàng Exception, loại gì, tham số gì:

Square root of x.
If x is negative, a domain error occurs: If a domain error occurs:

  • And math_errhandling has MATH_ERRNO set: the global variable errno is set to EDOM.
  • And math_errhandling has MATH_ERREXCEPT set: FE_INVALID is raised.

Việc bạn không kiểm tra object = null có thể chấp nhận được vì gọi kiểu nào nó cũng raise một exception phổ biến là NullPointerException (Java) - chứ không có nghĩa là các trường hợp tương tự bạn cũng làm như vậy. Không đảm bảo kiểm tra edge cases là sai cơ bản về kỹ thuật, nó là một việc hàm đó phải làm.

cái này là trick rồi, không tính là lỗi nữa, cơ mà công nhận dễ nhầm thật :joy: , cái này phải Raise ArgumentError

1 Like

This post was flagged by the community and is temporarily hidden.

#include <iostream>

int getScMax(int*, int);

int main() {
	int arr[10] = {1,7,9,6,23,56,32,32,5,56};
	std::cout << getScMax(arr,10) << std::endl;
}

int getScMax(int *arr, int n) {
	int max = 0;
	int scMax = 0;
	for (int i = 0; i < n; i++) {
		if (arr[i] > max) {
			scMax = max;
			max = arr[i];
		}
		else if (arr[i]<max && arr[i]>scMax) {
			scMax = arr[i];
		}
	}
	return scMax;
}
2 Likes

Hồi phỏng vấn ở Capegini cũng làm kiểu sắp ấy, xong họ ok nhưng gợi ý dùng 1 vòng for, cũng làm dùng 2 kia temp như trên. mỗi câu hỏi người phỏng vấn luôn có ý đồ nào đó, nắm được thì tốt. như câu trên họ hỏi mình là hướng tới performance.
Sau đó hỏi thêm 1 câu : kiêm tra mảng int có dạng hình sin hay không. Cái này thì muốn bắt tất cả exception.

1 Like
#include<stdio.h>
#include<stdlib.h>

void thuhai(int a[],int kichthuoc);
int main()
{
int a[10];
for(int i=0;i<10;i++)
{
    printf("moi ban nhap phan tu thu %d:",i+1);
    scanf("%d",(a+i));
}
thuhai(a,10);
}
void thuhai(int a[],int kichthuoc)
{
for(int i=0;i<9;i++)
    {
        for(int j=i+1;j<10;j++)
        {
                if(a[j]<a[i])//sap xep cac phan tu trong mang thoe thu tu tang dan
            {
            int k=a[i];
            a[i]=a[j];
            a[j]=k;
            }
        }
    }
printf("phan tu lon thu 2 trong mang la :%d",a[8]);
}

đây là code của em anh ý tưởng của em là sắp xếp các phần tử trong mảng theo thứ tự lớn dần và sau đó in ra phần tử lớn thứ 2 mong anh cho ý kiến ạ em cảm ơn anh @ltd

Tất cả các phần tử trong mảng như nhau thì sao?
Mảng chỉ có 1 tử thì sao :joy::joy::joy:

2 Likes

tôi không xét mảng có 1 phần tử mà ông giống nhau thì chơi tất

Mình thấy ngôn ngữ R khá hay trong toán học và phân tích dữ liệu. Hi vọng trong diễn đàn mình cũng có nhiều người nghiên cứu ngôn ngữ này.

Sử dụng sort

second <- function(x,k){
    y <- x[!is.na(x)]
    z <- y[duplicated(y) == FALSE]
    sort(z, decreasing =  TRUE)[k]
}

Không sử dụng sort

second2 <- function(x,k){
    y <- x[!is.na(x)]
    if(length(y) < k){
        paste("So phan tu thuc cua x nho hon", k)
    } else if(k == 1){
        max(y)
    } else {
        for(i in 1:(k-1)){
            z <- max(y)
            y <- y[y != z]
        }
    max(y)
    }
}
1 Like

Góp vui :smile:

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;

int main(){
	vector<int> vInt;
	vInt.push_back(3); vInt.push_back(4);
	vInt.push_back(8); vInt.push_back(7);
	vInt.push_back(2); vInt.push_back(9);


	if (vInt.size() > 1) {
		nth_element(vInt.begin(), vInt.begin()+1, vInt.end(), greater<int>());
		cout << vInt[1];
	} else {
		cout << "There's only one element in your array!";
	}
	
	return 0;
}
1 Like

https://www.google.com/search?q=find+2nd+largest+element+in+array&oq=find+2nd+&aqs=chrome.1.69i57j0l7.5712j0j7&sourceid=chrome&ie=UTF-8

theo google thì cho thấy 115tr kết quả :)) k yêu cầu tốc độ thì việc gì k dùng a gồ :smiley:

:smiley: Không sort, không max, không unique – tất cả hãy để map lo ! ^^

#include <iostream>
#include <map>
using namespace std;

int main()
{
    map<int,bool> OK;
    int A[10]={11,45,67,1000,43,86,32,56,89,54};

    for (int i=0;i<10;i++)
       OK[A[i]]=true;

    map<int,bool>::iterator p=OK.end();
    p-- =  p--;
    cout<<"Second element in the descending array: "<<p->first;

}
1 Like

Sắp xếp theo thứ tự tăng dần, xong rồi xuất ra phần tử đứng thứ 2 từ cuối đếm lên. Có cao nhân nào có cách tối ưu hơn không! :slight_smile:

public static void main(String[] args) {
    int []mang = {2,5,7,65,11,335,235};
    int choice = 0;
    for(int i =0;i<mang.length;i++)
    {
        for(int j =0;j<mang.length;j++)
        {
            if(mang[i]<mang[j])
            {
                choice = mang[i];
                mang[i] = mang[j];
                mang[j] = choice;
            }
        }
    }
    System.out.println("So lon nhi trong mang la:"+" "+mang[mang.length-2]);
} }

Dùng 2 vòng lặp :slight_smile:

  • 1 vòng lặp xác định xem coi có số nhỏ thử 2 hay ko
  • 1 vòng lặp xác định số nhỏ thứ 2

Bạn thử giải thích code đi :smiley:

Hi,
Do map lưu trữ các khóa của mình bằng cây nhị phân (cân bằng) nên khi chèn một phần tử vào khóa thì nó được đặt vào vị trí phù hợp trên cây lưu trữ (thỏa mãn thứ tự).

Để truy xuất các khóa lưu trữ trên cây, mình dùng con trỏ (không phải kiểu thuần túy trong C) mà là map::iterator

  • Ban đầu con trỏ trỏ tới phần tử “trái nhất” map::begin trên cây (đây là phần tử bé nhất theo quy luật trong cây nhị phân tìm kiếm)

  • Kiểu con trỏ này đã được định nghĩa toán tử ++.

  • Khi con trỏ được gọi toán tử ++ thì nó sẽ “trỏ” tới phần tử X mà X là phần tử tiếp theo khác rỗng trong thứ tự giữa duyệt cây- thứ tự này bảo đảm cho ra dãy tăng dần)

  • Còn map::end = ( con trỏ tới phần tử phải nhất- tức là to nhất)++ để báo hiệu kết thúc .

Còn toán tử -- thì làm ngược lại, đi từ lớn nhất sang nhỏ nhất

Do đó mình lấy con trỏ ở cuối lùi về 2 bước là ra được phần tử lớn nhì á !! :smiley:

1 Like

Nếu đã xài lib thì sao không xài cái này: http://en.cppreference.com/w/cpp/algorithm/nth_element

Mình dùng thuật toán này có sao không :smiley: (int? giống int nhưng cho phép null, kiểu như bool? của C# í)

void int? Lớn_thứ_nhì(List<int> ahjhj)
{
    int LonNhat = ahjhj[0];
    int? LonNhi = null;
    for (int i = 0; i < ahjhj.Count; i++)
        if (ahjhj[i] > LonNhat)
        {
            LonNhi = LonNhat;
            LonNhat = ahjhj[i];
        }
    return LonNhi;
}

O(n)

Cái này chắc là được :smiley:


Sử dụng 1phần heap sort là được.

Duyệt tuần tự nó vẫn nhanh hơn. Nếu là thứ k thì dùng Quickselect.

83% thành viên diễn đàn không hỏi bài tập, còn bạn thì sao?