C ++ 용 LINQ 라이브러리가 있습니까? [닫은]


82

어떤 방식 으로든 C ++에서 LINQ를 사용하기위한 플랫폼에 구애받지 않는 (CLI가 아님) 움직임이 있습니까?

전 세계 서버 프레임 워크의 상당 부분이 UNIX에서 실행되고 UNIX에서 LINQ for C ++에 액세스하면 많은 사람들이 만족할 것입니다!


1
모나드 (IEnumerable <> 및 그에 대한 확장 메서드 집합)를 의미합니까? 그것의 언어 측면을 의미합니까? LINQ-to-SQL을 의미합니까?
yfeldblum

LINQ-SQL 부분은 제가 정말 원하는 부분이지만 LINQ의 언어와 모나드에 따라 다릅니다.
Robert Gould

2
정말 도움이되는 질문입니다! 이와 같은 질문을 닫지 마십시오!
j00hi

암시 를 확인하십시오. github.com/DevUtilsNet/linqcpp 다른 구현을 분석하고 나에게 적합하지 않은 모든 결함을 제거했습니다.
antwoord

답변:


34

Hong Jiang의 Linq ++ 는 좋은 시작처럼 보입니다. 구문은 CLinq보다 Linq에 훨씬 더 가깝습니다. pfultz2의 Linq도 흥미로워 보이지만 C ++ 11 컴파일러가 필요합니다.


1
좋은. C ++ 11 버전은 그의 원시 이해 예제가 "상용구 코드"를 피하기 위해 Phoenix를 사용 했어야했지만 매우 흥미로워 보입니다.
KitsuneYMG

흠 SQL 데이터베이스를 지원하지 않습니다.
Arne

21

이것은 템플릿 C ++ LINQ 라이브러리의 솔루션입니다.
소스 코드는 다음과 같습니다. Boolinq
각 기능에 대한 많은 테스트가 있습니다.
지금 작업 중입니다.

다른하실 말씀 있나요?
조언이 될 수 있습니까?

업데이트 : 프로젝트가 https://github.com/k06a/boolinq 로 이동 했으며 이제 소스 코드가 700 줄에 불과한 버전 2.0이 있습니다. :)


에 관한 컴파일 오류로 인해 Qt 5.9.1에서 boolinq를 사용할 수 없습니다 Q_FOREACH. 아마도 Q_FOREACH단계적으로 중단 되었기 때문일 것입니다.
Nikola Malešević

@ NikolaMalešević 당신은 boolinq.h를 포함하기 직전에 정의를 시도 할 수 있습니다. #define foreach for_each그런 다음 include : 후에 #undef foreachQt 헤더를 포함하십시오.
k06a jul.

1
정말 Boolinq처럼! groupBy를 추가하십시오
pingu

18

Microsoft는 방금 C 및 C ++ 용 LINQ를 구축 했다고 발표 했습니다. 하지만 아직 사용할 수 없습니다.

2012 년 11 월 6 일 업데이트 :

Microsoft Open Technologies, Inc.는 이제 LINQ 구현 (Ix ++) 및 새로운 Rx ++ (Reactive Extensions) 라이브러리를 비롯한 여러 관련 라이브러리를 릴리스 하고 오픈 소스 (Apache License 2.0)했습니다.


8

http://cpplinq.codeplex.com/ 은 아주 좋은 구현입니다.
작성자 :
CppLinq의 동기는 boolinq와 Native-RX가 모두 연산자를 기반으로하는 것 같습니다. " 목록 함수를 작성합니다. 문제는 "." 연산자는 C ++에서 오버로드 될 수 없기 때문에 자체 디자인의 기능으로 이러한 라이브러리를 확장하기가 어렵습니다. 나에게 이것은 중요합니다. CppLinq는 오버로드 가능한 operator >>를 기반으로하므로 CppLinq를 확장 가능하게 만들 수 있습니다.


7

STL 범위에서 작동하고 많은 LINQ 유사 함수를 제공하는 강력하게 강화 된 라이브러리 인 PSade.Oven을 살펴볼 수 있습니다 .


아주 흥미 롭 네요. 기회가 생기면 한번 볼게요, 고마워요!
Robert Gould

7

IEnumerable <> 및 해당 LINQ 연산자를 다시 구현 하는 작은 라이브러리 cppLinq 를 작성했습니다 . 단지 실험 일뿐입니다. 현재로서는 Windows에서만 작동하며 (코 루틴은 Win32 파이버로 구현 됨) VS11의 Dev Preview로만 빌드됩니다 (람다 표현식을 많이 사용합니다 :-)).

다음과 같은 코드를 작성할 수 있습니다.

auto source = IEnumerable<int>::Range(0, 10);

auto it = source->Where([](int val) { return ((val % 2) == 0); })
                ->Select<double>([](int val) -> double { return (val * val); }));

foreach<double>(it, [](double& val){
    printf("%.2f\n", val);
});

7
맹목적으로 C #을 C ++로 변환하는 것은 아무에게도 좋은 일이되지 않습니다. 인터페이스가 필요한 이유는 무엇입니까? 그것들을 제거하면 쓸모없는 할당과 더 복잡한 구문도 모두 제거됩니다. 그리고 할 수 없다면 적어도 shared_ptrs를 unique_ptrs로 전환하십시오 . 후자는 전자로 변환 될 수 있지만 그 반대의 경우는 불가능합니다. 또한 스타일, -> double반환 유형이 필요하지 않습니다 . 암시 적 변환이 제 역할을하도록하세요.
Xeo

2
귀하의 의견에 감사드립니다. 예, 위 샘플의 람다는 약간 개선 될 수 있지만 세부 사항 일뿐입니다. 그래도 shared_ptrs 및 포인터에 대해 무엇을 할 수 있는지 잘 모르겠습니다. 아이디어는 지연 평가 및 데이터 파이프 라인을 제공하기 위해 코 루틴으로 반복기 블록을 구현하는 것이 었습니다. C #에서 정확히 구현되는 방식입니다. 예를 들어 소스에는 STL 컨테이너에서 데이터를 "생성"하는 무언가가있을 수 있지만 IEnumerator처럼 동작해야하는 구성 요소 파이프가있어 공동 루틴에서 데이터를 생성합니다. LINQ의 C ++ 버전에 대해 염두에두고있는 인터페이스는 무엇입니까?
Paolo Severini 2012

5
정적 인 표현식 템플릿 기반 접근 방식을 염두에 두었습니다. 그것에 대해 읽어보십시오.
Xeo

감사합니다, Xeo, 정말! 표현식 템플릿은 매우 흥미 롭습니다. 이에 대해 더 많이 배우려고 노력할 것입니다. LINQ 의미에서 지연 평가를 구현하는 데 사용할 수 있다고 생각하십니까 (시퀀스가 한 번에 한 항목 씩 "수율"됨)? 왜냐하면 이것이 LINQ의 요점이라고 생각하기 때문입니다. 기존 컨테이너를 수정하고 싶지 않습니다. LINQ 식에 연결된 모든 연산자의 출력 인 임시 컨테이너에 대한 모든 데이터를 한 번에 생성하고 싶지 않습니다. 게으르지 않으면 LINQ를 귀찮게 할 필요가 없습니다. stl, std 알고리즘 및 람다로 모든 작업을 수행 할 수 있습니다.
Paolo Severini 2012

2
음 .. 반복자의 역 참조 중에 만 원하는 것을 적용하십시오. 또한 Boost.Range를 살펴보십시오 .
Xeo

3

여기에 단순히 boost 및 stl 알고리즘에 대한 래퍼 인 또 다른 대안 이 있으므로 이러한 구현의 대부분의 성능 이점을 얻을 수 있습니다.

다음과 같이 작동합니다.

std::vector<int> xs;
auto count = from(xs)
   .select([](int x){return x*x;})
   .where([](int x){return x > 16;})
   .count();
auto xs2 = from(xs)
   .select([](int x){return x*x;})
   .to<std::vector<int>>();

일부 메소드는 빈 범위에 대한 프록시를 반환합니다.

std::vector<int> xs;
auto max = from(xs)
   .select([](int x){return x*x;})
   .where([](int x){return x > 16;})
   .max()
   .value_or(default_max_value);

피드백을 환영합니다.


아주 잘 했어요, 좋아요.
Tim Sylvester 2015 년

3

실제로 목록 이해를 위해 Linq를 사용하려는 경우이 Linq 라이브러리를 사용할 수 있습니다 . C ++ 11 (MSVC 2010에서 작동)과 Boost가 필요합니다. 라이브러리를 사용하면 다음과 같이 linq 쿼리를 작성할 수 있습니다.

struct student_t
{
    std::string last_name;
    std::vector<int> scores;
};

std::vector<student_t> students = 
{
    {"Omelchenko", {97, 72, 81, 60}},
    {"O'Donnell", {75, 84, 91, 39}},
    {"Mortensen", {88, 94, 65, 85}},
    {"Garcia", {97, 89, 85, 82}},
    {"Beebe", {35, 72, 91, 70}} 
};

auto scores = LINQ(from(student, students) 
                   from(score, student.scores) 
                   where(score > 90) 
                   select(std::make_pair(student.last_name, score)));

for (auto x : scores)
{
    printf("%s score: %i\n", x.first.c_str(), x.second);
}

다음을 출력합니다.

Omelchenko score: 97
O'Donnell score: 91
Mortensen score: 94
Garcia score: 97
Beebe score: 91

2

C ++ 0x 또는 그것이 호출되는 모든 것은 auto유형 추론을 허용 하는 새로운 키워드를 가지고 있습니다. 그리고 예, C ++에 람다가 올 것입니다. 또한 빠른 Google 검색을 통해 CLinq라는 사실이 밝혀졌습니다 .


2

다음은 C ++ 11 (중국어)을 사용한 C ++-linq 구현입니다.

http://www.cnblogs.com/cbscan/archive/2012/10/20/2732773.html

"지연된 쿼리", "스택 기반"(가능한 한 적은 새 연산자 사용), "시맨틱 복사"(백업 후 쿼리를 여러 번 반복 할 수 있음) 등과 같은 기능을 지원합니다.

또한 "from, select, where, cast, range, all, any, cast, average, contain, count, first, last, head, tail, groupBy, takeUntil, skipUntil, max, min, reduce, 고유, 정렬, 임의, 교차, _union ".

내 코드는 누구나 이해하고 확장 할 수있을만큼 간단하다고 생각합니다.


-4

나는 C ++에 람다 식과 같은 것을 처리 할 수있는 컴파일러 설탕이 없다고 생각한다. 그래서 그런 일은 일어나지 않을 것이다.


5
C ++ 0X에는 람다가 있으므로 이론적으로는 가능해야하지만 쉬운 작업은 아닙니다.
Robert Gould

7
Boost.Phoenix 라이브러리는 또한 사전 컴파일러 트릭없이 C ++에 Lambda를 추가합니다. tinyurl.com/d4y9se [boost.org]를 참조하십시오 . 물론 C ++ 0x를 사용하면이 작업이 훨씬 쉬워집니다! c ++ 0x tinyurl.com/d9zlsc [blogspot.com]
jk로

3
LOL, boost :: lambda, 일부 템플릿 속임수 및 특정 경우 사전 컴파일러의 도움으로 다음 구문을 만들 수있었습니다 from(v).where(&_1 ->* &Person::age >= 18).order_by(Person, age).top(5).order_by(Person, name). std :: vector <Person>에서 가장 어린 성인 다섯 명을 선택하고 반환합니다. 알파벳 순서로. 나는 C + +를 ... 작업에 적합 말할 것 그래서
안드레아스 그누

1
@Andreas, 오, LINQ의 초능력을 사용하여 LINQ를 SQL 쿼리로 변환하고 있다고 생각했습니다. 이 경우 AST가 필요하고 C #으로 가져옵니다. C ++ AFAIK에서는 그렇게 할 수 없습니다.
Elazar Leibovich 2011 년

1
@Elazar & @Andreas-LINQ에는 실제로 두 가지 맛이 있습니다. 하나는 Andreas의 방식대로 작동하고 다른 하나는 SQL 또는 기타 쿼리 표현을 생성하기 위해 코드에서 재 해석 될 수있는 표현식 트리 (전체 AST의 하위 집합)를 사용합니다. 후자의 양식에 대한 자세한 내용 Expression<T>은 C # 설명서를 참조하십시오.
Drew Noakes 2011-06-28
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.